June 12, 2026 · 6 min read · Data

Tokyo's 23 special wards: not boroughs, not cities, something else.

Tokyo doesn't have a mayor. It has a governor of Tokyo Metropolis, plus 23 special-ward mayors, plus 26 city mayors, plus a handful of town and village heads. There is no single municipal entity called "Tokyo." Every travel app pretends there is, and so must your data.

The legal structure

Tokyo Metropolis (Tōkyō-to) is a prefecture. Inside it sit:

When a tourist says "Tokyo," they mean the 23 wards plus maybe Mitaka (for Ghibli Museum) and Tachikawa (sometimes, for Showa Memorial Park). They almost never mean Hachioji or the Ogasawara Islands.

Why this breaks naive APIs

A flat city table that treats Shibuya, Shinjuku, and Minato as separate top-level cities (because legally they are) will fail on every "Tokyo" query. The user types "best ramen in Tokyo," your code looks up city_id for "Tokyo," gets back nothing or the prefecture-level row with no venues attached, and returns an empty list.

A flat city table that treats only "Tokyo Metropolis" as the entity has the opposite problem: every venue is attributed to the prefecture, you can't distinguish Shibuya from Adachi, and your "near me" queries lose all neighborhood-level granularity.

Both are wrong. The correct shape is a hierarchical city that exposes a Tokyo entity for human-facing queries while preserving ward-level attribution underneath.

What the API returns

GET /v1/cities/tokyo

{
  "city_id": "tokyo",
  "name": "Tokyo",
  "iso_alpha2": "JP",
  "aggregates_neighborhoods": true,
  "child_city_count": 23,
  "tier": 1,
  "context": {
    "airport": { "iata": "HND", "name": "Haneda" },
    "currency": "JPY",
    "timezone": "Asia/Tokyo"
  }
}

A query for restaurants in Tokyo fans out across all 23 wards, ranks them globally, and returns the top results tagged with their actual ward:

GET /v1/restaurants?city_id=tokyo&limit=5

[
  { "name": "Sukiyabashi Jiro Honten", "tier": "1 Star", "ward": "Chuo" },
  { "name": "Kanda",                   "tier": "3 Stars", "ward": "Minato" },
  { "name": "Quintessence",            "tier": "3 Stars", "ward": "Shinagawa" },
  { "name": "Ryugin",                  "tier": "3 Stars", "ward": "Chiyoda" },
  { "name": "Ishikawa",                "tier": "3 Stars", "ward": "Shinjuku" }
]

The same pattern, elsewhere

Tokyo isn't unique in being legally fragmented:

For each, aggregates_neighborhoods: true is the flag that says "treat this as one city for query purposes, even though the law says otherwise." The child_city_count tells you how big the union is.

One practical caveat

The 23-ward rollup excludes the western cities and the islands. If your user is genuinely planning a trip to Hachioji or Ogasawara, the right call is to query those as separate cities. The Tokyo rollup is a tourist abstraction; don't confuse it with administrative truth, and don't confuse administrative truth with what tourists need.

Sign up — free See India coverage →