Developers
Kuramap API
A read-only JSON API over Kenya's counties, constituencies and wards - and the people who currently represent each one. Call it anonymously, or with a free API key for a higher, attributable quota.
Before you build on it, read where the data comes from and what's known to be wrong with it - it also carries the licence and attribution terms for reuse.
Getting started
-
Sign up
Go to the developer dashboard and enter your email. We send a one-time magic link - no password.
-
Create a key
From the dashboard, choose Create key. Your key is shown exactly once - copy it now. We store only a hash and the non-secret prefix (
km_live_<id>), so we can't show it again. Lost it? Revoke and create another. -
Make your first request
Pass the key as a bearer token. (Drop the header for anonymous, cacheable access.)
curl -sS \ -H "Authorization: Bearer km_live_3f9a1c20…" \ https://kuramap.euxven.com/api/v1/ke/counties/nairobi -
Mind the rate limits
The free tier allows 10,000 requests/day with a 600 requests/minute burst. Every keyed response carries
X-RateLimit-Limit,X-RateLimit-RemainingandX-RateLimit-Reset(Unix seconds to the next 00:00 UTC reset). Over the limit returns429with aRetry-Afterheader - back off and retry.
Client snippets
JavaScript (fetch)
const res = await fetch(
"https://kuramap.euxven.com/api/v1/ke/representatives?role=governor®ion=nairobi",
{ headers: { Authorization: "Bearer km_live_3f9a1c20…" } },
);
if (res.status === 429) {
const retry = res.headers.get("Retry-After");
throw new Error(`Rate limited; retry after ${retry}s`);
}
const page = await res.json();
console.log(page.items, "of", page.total); Python (requests)
import requests
resp = requests.get(
"https://kuramap.euxven.com/api/v1/ke/lookup",
params={"lat": -1.2921, "lng": 36.8219},
headers={"Authorization": "Bearer km_live_3f9a1c20…"},
timeout=10,
)
resp.raise_for_status()
print(resp.headers.get("X-RateLimit-Remaining"), "requests left today")
print(resp.json()["ward"]["name"]) Versioning & deprecation
The API is versioned in the path: /api/v1. Within v1 we only make
backward-compatible changes - new endpoints, new optional
query parameters, and new fields on existing objects. Write your client to
ignore unknown fields and unknown enum values so these additions
never break you.
A breaking change - removing or renaming a field, changing
a type, or altering response semantics - would ship under a new major path
(/api/v2), running alongside
v1. Anything slated for removal is
marked deprecated here first, with a published sunset window, before it
is withdrawn.
API reference
The full, generated reference - every endpoint, parameter and schema - lives on its own page. You can also fetch the raw spec at /openapi.yaml (OpenAPI 3.1).