Search API

Find places by name or address, or look up what is at a coordinate.

Search is available on paid plans only — Starter, Pro and Enterprise. A free-plan key gets 403 on /search, /search/structured and /reverse; see Errors for the exact response and Pricing for the plans.

Billing1 unit per request (/search, /search/structured and /reverse alike)
DataOpenStreetMap, powered by Photon
CoverageEurope
PlanPaid plans only (Starter, Pro, Enterprise). Free-plan keys get 403.
Languagescs, en, sk, pl, de, or default for each place’s local name
FormatGeoJSON FeatureCollection, coordinates as [lon, lat]

Find places by name or address. Built for search-as-you-type: send a request on every keystroke (debounced) and partial words still match.

GET /search?q={query}&apiKey=<key>

Parameters

ParameterDescription
qSearch text (required)
limitMaximum number of results (default 15, max 50)
langResult language: cs, en, sk, pl, de, or default for local names. Without lang, the Accept-Language header decides, so browsers get their user’s language when it is supported. Any other value returns HTTP 400.
lat, lonPrefer results near this point (location bias)
zoom, location_bias_scaleHow strongly to apply the location bias: a lower zoom (default 12, roughly a map zoom) covers a wider area, and location_bias_scale (0.0–1.0, default 0.4) sets how much prominence counts against distance
bboxOnly return results inside minLon,minLat,maxLon,maxLat
osm_tagFilter by OSM tag, repeatable: key:value, key, :value, or negated with ! (e.g. osm_tag=natural:peak, osm_tag=!highway)
layerFilter by type, repeatable: house, street, locality, district, city, county, state, country, other
countrycodeOnly return results in this ISO 3166-1 alpha-2 country; repeat for several (countrycode=CZ&countrycode=SK)
dedupeSet 0 to keep duplicate results (such as one street split into several OSM ways)

Example

GET https://api.mapriot.com/search?q=Ještěd&osm_tag=natural:peak&lang=en&limit=1&apiKey=<key>

Response

{
  "type": "FeatureCollection",
  "features": [
    {
      "type": "Feature",
      "properties": {
        "osm_type": "N",
        "osm_id": 308351899,
        "osm_key": "natural",
        "osm_value": "peak",
        "type": "other",
        "name": "Ještěd",
        "city": "Liberec",
        "county": "okres Liberec",
        "state": "Liberec Region",
        "country": "Czechia",
        "postcode": "460 08",
        "countrycode": "CZ"
      },
      "geometry": { "type": "Point", "coordinates": [14.9839199, 50.7327738] }
    }
  ]
}

Areas such as cities, streets, and parks also include extent: [minLon, maxLat, maxLon, minLat]. Use it to fit the map to the result.


Search by address fields instead of free text.

GET /search/structured?city=Brno&street=Masarykova&housenumber=1&apiKey=<key>

Fields: countrycode, state, county, city, postcode, district, street, housenumber. The common parameters limit, lang, lat/lon, bbox, osm_tag and layer also work here.


Reverse geocoding

Find the nearest place to a coordinate.

GET /reverse?lat={lat}&lon={lon}&apiKey=<key>
ParameterDescription
lat, lonCoordinate (required)
radiusSearch radius in km
limitMaximum number of results (default 1, max 50)
lang, osm_tag, layerSame as for search

Example

GET https://api.mapriot.com/reverse?lat=50.0875&lon=14.4213&lang=en&apiKey=<key>
{
  "type": "FeatureCollection",
  "features": [
    {
      "type": "Feature",
      "properties": {
        "osm_type": "W", "osm_id": 340086966,
        "osm_key": "tourism", "osm_value": "attraction", "type": "house",
        "name": "Prague Meridian", "street": "Old Town Square", "district": "Josefov",
        "city": "Prague", "postcode": "110 00", "country": "Czechia", "countrycode": "CZ"
      },
      "geometry": { "type": "Point", "coordinates": [14.4213299, 50.0874765] }
    }
  ]
}

Add layer=street to get the nearest street instead of the nearest point of interest.


Autocomplete from a browser

Search is a plain GET, so browsers send it without a CORS preflight. Debounce keystrokes and bias the results towards the visible map:

let timer;
input.addEventListener('input', () => {
  clearTimeout(timer);
  timer = setTimeout(async () => {
    const { lng, lat } = map.getCenter();
    const params = new URLSearchParams({
      q: input.value, limit: '5', lang: 'en',
      lat: String(lat), lon: String(lng), zoom: String(Math.round(map.getZoom())),
      apiKey: '<key>',
    });
    const res = await fetch(`https://api.mapriot.com/search?${params}`);
    const { features } = await res.json();
    // features[i].geometry.coordinates is [lon, lat]
  }, 250);
});

Each request costs 1 unit, so a 250 ms debounce keeps a typical search at 3–5 units.


Errors

StatusCause
400Invalid parameter, such as an unsupported lang, a missing q, or an unknown parameter. The body is JSON naming the parameter, e.g. {"lang": [{"message": "Language is not supported. Supported are: default, cs, de, sk, en, pl, es", "value": "fr"}]}
403Missing, invalid, or restricted API key — or search is not included in your plan (free plan). Plain-text body: This feature is not available on your plan. See https://mapriot.com/pricing for details or contact us at support@mapriot.com. A rejected request is not billed.
429Free-tier hard cap reached (200% of the monthly limit)

Responses are cacheable for 5 minutes (Cache-Control: public, max-age=300).