MyShortAddress API
Turn coordinates or a Saudi Short Address (e.g. RCDA6608) into a full, structured national address — district, street, building number, postal code and more — with one HTTPS call.
https://your-hostHTTPS · JSON
X-API-Key header1 credit per new Short Address — no Short Address, or the same address again within 7 days, is free
- Every map link — Google Maps pins, places and businesses, links copied from the browser, Apple Maps, Waze, OpenStreetMap. Input types
- Always an answer — no Short Address on the exact point returns the nearest registered building's within 100 m, flagged in
nearest. Response - Search by place name —
GET /api/v1/search, then look up theplace_id. Name search - Fair billing — you pay only for new addresses found. Credits
Authentication
Every request must carry your secret API key in the X-API-Key header. You can also use Authorization: Bearer <key>.
X-API-Key: sat_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
Your key is shown once, when you generate it in the Console → API tab. We store only a hashed version, so we can never show it again. Lost it? Regenerate — the old key stops working instantly. Keys are secret: keep them on your server, never in a mobile app or browser.
The lookup endpoint
/api/v1/lookup
Send a JSON body with an input and an optional language.
| Field | Type | Required | Description |
|---|---|---|---|
| input | string | Yes | Coordinates "24.71,46.67" or a Short Address "RCDA6608". |
| language | string | No | "en" (default) or "ar". |
Input types
Coordinates
Latitude, longitude. "24.7136, 46.6753". Returns the full national address incl. the Short Address.
Short Address
The 8-char Saudi code. "RCDA6608". Resolves to coordinates + full address.
Map links
Google Maps (short and full links, dropped pins, links copied from the browser), Apple Maps, Waze, OpenStreetMap, HERE, Bing and Petal links, plus degrees-minutes-seconds and plus codes.
Google place links
A shop, office or area shared from Google Maps without a pin is placed on Google's own location for that place, then looked up like a pin.
Search by place name
Find a place — a shop, company, mall or landmark — by its name, then look it up by the place_id you pick. Included in every paid pack; a free account can try it 3 times. The search itself uses no credit.
GET /api/v1/search?q=Kingdom%20Centre&language=en
X-API-Key: sat_...
200 OK
{
"results": [
{ "place_id": "ChIJ...", "name": "Kingdom Centre",
"area": "King Fahd Road, Riyadh Saudi Arabia" }
],
"paid": true,
"free_tries_left": null
}
POST /api/v1/lookup
{ "place_id": "ChIJ...", "label": "Kingdom Centre", "language": "en" }
The lookup answers exactly like any other lookup, plus place_name. Errors: 402 name_search_locked when the free tries are used up, 400 query_too_short under 3 characters.
Response
A 200 OK returns the structured address. Fields that can't be resolved are null.
{
"short_address": "RCDA6608",
"formatted": "Al Aqiq, Riyadh 13515, Saudi Arabia",
"building_number": "6608",
"street": "Anas Ibn Malik Road",
"district": "Al Aqiq",
"city": "Riyadh",
"region": "Riyadh",
"postal_code": "13515",
"additional_number": "2745",
"country": "Saudi Arabia",
"lat": 24.7563,
"lng": 46.6295,
"resolved_via": "national_address",
"cached": false,
"credits_remaining": 4871,
"input": "24.7563, 46.6295"
}
When the pin is not on a registered building
A Short Address belongs to a registered building. If the point is on a street, a car park or open land, you get the Short Address of the nearest registered building within 100 m, and two extra fields say so. Beyond 100 m, short_address is null and no credit is used.
{
"short_address": "RRRA3218",
"nearest": {
"short_address": "RRRA3218",
"distance_m": 23,
"lat": 24.87922,
"lng": 46.62253
},
"short_address_note": "Nearest registered building, 23 m from this point",
"lat": 24.8791221,
"lng": 46.6227282,
"...": "the other fields describe that building"
}
cached: true means the result was served from our cache — it still counts as one credit but returns in milliseconds. credits_remaining is null for bring-your-own-key accounts.
Code examples
curl -X POST https://your-host/api/v1/lookup \
-H "X-API-Key: sat_YOUR_KEY" \
-H "Content-Type: application/json" \
-d '{"input": "24.7136, 46.6753", "language": "en"}'
Batch lookups
Have a long list? Send up to 1,000 inputs in one request instead of one request each. The batch is looked up in the background at a steady pace, and you collect the results when it's done. Billing is the same as the bulk CSV: 1 credit per new Short Address found; inputs with no Short Address, repeats and errors are free.
/api/v1/batch
curl -X POST https://your-host/api/v1/batch \
-H "X-API-Key: sat_YOUR_KEY" \
-H "Content-Type: application/json" \
-d '{"inputs": ["24.7563,46.6295", "RCDA6608", "https://maps.app.goo.gl/..."], "language": "en"}'
The answer is 202 Accepted with a batch_id:
{
"batch_id": "3f9c2a7d41e0b8c65d12",
"status": "queued",
"total": 3,
"done": 0
}
/api/v1/batch/{batch_id}
Ask every few seconds. While status is queued or running you see the progress (done of total). When it is done, results lists every input in the order you sent it, with the address fields of a single lookup plus status (it starts with ok when the address was found) and error.
{
"batch_id": "3f9c2a7d41e0b8c65d12",
"status": "done",
"total": 3, "done": 3, "ok": 2, "errors": 1, "skipped": 0,
"results": [
{"input": "24.7563,46.6295", "status": "ok", "short_address": "RCDA6608",
"building_number": "6608", "street": "Anas Ibn Malik Road", "district": "Al Aqiq",
"city": "Riyadh", "postal_code": "13515", "additional_number": "2745", "...": "..."},
{"input": "RCDA6608", "status": "ok - free, already looked up", "...": "..."},
{"input": "https://maps.app.goo.gl/...", "status": "error",
"error": "This link shares a place name, not a pin on the building...", "...": "..."}
]
}
Stop a batch with POST /api/v1/batch/{batch_id}/cancel — inputs not looked up yet use no credit. Results stay available for 7 days. Errors: 400 inputs_required, 413 too_many_rows (over 1,000 inputs), 402 insufficient_credits (your balance is lower than the number of inputs), 429 queue_full (10,000 inputs already waiting).
Errors
Errors return a non-2xx status and a JSON body with an error code and human-readable message.
| Status | error | Meaning |
|---|---|---|
| 400 | input_required | Missing or unparseable input. |
| 401 | api_key_required / invalid_api_key | Missing key, or the key is wrong / API access disabled. |
| 402 | out_of_credits | Your credit balance is 0. Top up to continue. |
| 403 | account_suspended | The account is suspended. |
| 429 | rate_limited | Too many requests — see Retry-After header. |
| 502 | lookup_failed | No provider could resolve the point. No credit is charged. |
You are only charged for successful lookups. Failed and invalid requests never consume a credit.
Rate limits
The API allows up to 120 requests per minute per account. Exceeding it returns 429 with a Retry-After header (seconds). For a long list, send a batch of up to 1,000 inputs instead. Repeated identical lookups are served from cache and are much faster.
Credits & billing
You pay only for new addresses. 1 credit is used when a lookup returns a Short Address you haven't looked up recently. These are free:
- a lookup that finds no Short Address (no building within 100 m) — the response says
"charged": false - the same Short Address again within 7 days (
free_reason: "repeat") - place-name suggestions from
/api/v1/search
The web app, bulk CSV and API draw from the same shared balance. Buy credit packs in the Console → Billing tab. Watch credits_remaining in each response, and top up before you hit zero to avoid 402 errors.
Security best practices
- Call the API from your backend server only. Never embed the key in a mobile app, browser JavaScript, or public repo.
- Store the key in an environment variable / secrets manager — not in source code.
- Always use HTTPS (the API rejects plain HTTP at the proxy).
- Rotate the key immediately if you suspect it leaked — regenerating instantly invalidates the old one.
- Disable API access from the Console when you're not using it; the key is preserved and can be re-enabled anytime.
Ready to integrate?
Generate your key in the console and make your first call in minutes.