Skip to content

District Pages API Documentation

This document provides API documentation for building congressional district pages, intended for the cbpublic team.

Developer Resources

CLAUDE.md - AI-assisted development guide

Overview

The Congressional Districts API provides structured data about U.S. congressional districts including: - Census demographic data (population, income, education, etc.) - Geographic boundaries (GeoJSON) - Wikipedia-sourced information (representative, party, Cook PVI)

Base URL: https://districts.nominate.ai/api/v1

Authentication

No authentication required. Public API.

Endpoints

Get District Details

GET /api/v1/districts/{geoid}

Returns census demographic data for a district.

Parameters: - geoid (path, required): 4-digit Census GEOID (state FIPS + district number)

Example:

curl https://districts.nominate.ai/api/v1/districts/1903

Response:

{
  "geoid": "1903",
  "name": "Iowa's 3rd Congressional District",
  "state_fips": "19",
  "state_name": "Iowa",
  "population": 818737,
  "median_age": 36.8,
  "median_income": 72456,
  "bachelors_plus": 245621,
  "unemployment_rate": 3.2,
  "median_home_value": 198500
}


Get District Wikipedia Data

GET /api/v1/districts/{geoid}/wiki

Returns Wikipedia-sourced information including current representative, party affiliation, and Cook PVI.

Parameters: - geoid (path, required): 4-digit Census GEOID

Example:

curl https://districts.nominate.ai/api/v1/districts/1903/wiki

Response:

{
  "geoid": "1903",
  "state_code": "ia",
  "state_name": "Iowa",
  "district_number": 3,
  "is_at_large": false,
  "title": "Iowa's 3rd Congressional District",
  "summary": "Iowa's 3rd congressional district is a congressional district in the U.S. state of Iowa. It includes the Des Moines metropolitan area and extends into rural western Iowa.",
  "population": "818,737",
  "representative": "Zach Nunn",
  "party": "Republican",
  "cook_pvi": "R+3",
  "counties": ["Adair", "Adams", "Cass", "Dallas", "Guthrie", "Madison", "Polk", "Story", "Warren"],
  "wikipedia_url": "https://en.wikipedia.org/wiki/Iowa%27s_3rd_congressional_district",
  "cached_at": "2024-01-15T10:30:00+00:00",
  "cache_expires_at": "2024-01-17T10:30:00+00:00"
}

Cache Behavior: - Data is cached for 48 hours - cached_at and cache_expires_at indicate cache freshness - Stale cache is automatically refreshed on next request


Get District Geometry

GET /api/v1/districts/{geoid}/geometry

Returns GeoJSON geometry for the district boundary.

Example:

curl https://districts.nominate.ai/api/v1/districts/1903/geometry

Response: GeoJSON Feature with Polygon/MultiPolygon geometry


List All Districts

GET /api/v1/districts

Returns paginated list of all districts.

Query Parameters: | Parameter | Type | Default | Description | |-----------|------|---------|-------------| | limit | int | 50 | Max items (1-500) | | offset | int | 0 | Items to skip | | state_fips | string | - | Filter by state (2-digit FIPS) | | format | string | json | json or geojson | | include_geometry | bool | false | Include geometry data | | sort | string | geoid | Sort field | | order | string | asc | asc or desc |

Example:

# Get all Iowa districts
curl "https://districts.nominate.ai/api/v1/districts?state_fips=19"

# Get all districts as GeoJSON
curl "https://districts.nominate.ai/api/v1/districts?format=geojson&limit=500"


GEOID Reference

The GEOID is a 4-digit code: 2-digit State FIPS + 2-digit District Number

GEOID State District
0601 California 1st
0652 California 52nd
1903 Iowa 3rd
3600 New York At-large (if applicable)
4801 Texas 1st

At-Large Districts: District number is 00 (e.g., Alaska = 0200, Wyoming = 5600)

State FIPS Codes

FIPS State FIPS State
01 Alabama 28 Mississippi
02 Alaska 29 Missouri
04 Arizona 30 Montana
05 Arkansas 31 Nebraska
06 California 32 Nevada
08 Colorado 33 New Hampshire
09 Connecticut 34 New Jersey
10 Delaware 35 New Mexico
11 District of Columbia 36 New York
12 Florida 37 North Carolina
13 Georgia 38 North Dakota
15 Hawaii 39 Ohio
16 Idaho 40 Oklahoma
17 Illinois 41 Oregon
18 Indiana 42 Pennsylvania
19 Iowa 44 Rhode Island
20 Kansas 45 South Carolina
21 Kentucky 46 South Dakota
22 Louisiana 47 Tennessee
23 Maine 48 Texas
24 Maryland 49 Utah
25 Massachusetts 50 Vermont
26 Michigan 51 Virginia
27 Minnesota 53 Washington
54 West Virginia
55 Wisconsin
56 Wyoming

Integration Guide for cbpublic

Building a District Page

To build a comprehensive district page, combine data from multiple endpoints:

import httpx

async def get_district_page_data(geoid: str):
    """Fetch all data needed for a district page."""
    base = "https://districts.nominate.ai/api/v1"

    async with httpx.AsyncClient() as client:
        # Fetch census demographics
        census_resp = await client.get(f"{base}/districts/{geoid}")
        census_data = census_resp.json()

        # Fetch Wikipedia data (representative, party, summary)
        wiki_resp = await client.get(f"{base}/districts/{geoid}/wiki")
        wiki_data = wiki_resp.json()

        # Combine into page data
        return {
            "geoid": geoid,
            "name": census_data.get("name"),
            "state": wiki_data.get("state_name"),

            # From Census
            "population": census_data.get("population"),
            "median_income": census_data.get("median_income"),
            "median_age": census_data.get("median_age"),
            "unemployment_rate": census_data.get("unemployment_rate"),

            # From Wikipedia
            "representative": wiki_data.get("representative"),
            "party": wiki_data.get("party"),
            "cook_pvi": wiki_data.get("cook_pvi"),
            "summary": wiki_data.get("summary"),
            "counties": wiki_data.get("counties"),
            "wikipedia_url": wiki_data.get("wikipedia_url"),
        }

Converting District Code to GEOID

If you have a district code like "ia03", convert to GEOID:

STATE_TO_FIPS = {
    "al": "01", "ak": "02", "az": "04", "ar": "05", "ca": "06",
    "co": "08", "ct": "09", "de": "10", "dc": "11", "fl": "12",
    "ga": "13", "hi": "15", "id": "16", "il": "17", "in": "18",
    "ia": "19", "ks": "20", "ky": "21", "la": "22", "me": "23",
    "md": "24", "ma": "25", "mi": "26", "mn": "27", "ms": "28",
    "mo": "29", "mt": "30", "ne": "31", "nv": "32", "nh": "33",
    "nj": "34", "nm": "35", "ny": "36", "nc": "37", "nd": "38",
    "oh": "39", "ok": "40", "or": "41", "pa": "42", "ri": "44",
    "sc": "45", "sd": "46", "tn": "47", "tx": "48", "ut": "49",
    "vt": "50", "va": "51", "wa": "53", "wv": "54", "wi": "55",
    "wy": "56"
}

def code_to_geoid(code: str) -> str:
    """Convert district code (e.g., 'ia03') to GEOID (e.g., '1903')."""
    code = code.lower()
    state = code[:2]
    district = code[2:].zfill(2)
    fips = STATE_TO_FIPS.get(state)
    return f"{fips}{district}"

# Examples
code_to_geoid("ia03")  # -> "1903"
code_to_geoid("ca52")  # -> "0652"
code_to_geoid("ak00")  # -> "0200" (at-large)

Error Handling

async def safe_get_wiki_data(geoid: str):
    """Fetch Wikipedia data with error handling."""
    try:
        resp = await client.get(f"{base}/districts/{geoid}/wiki")
        if resp.status_code == 404:
            return None  # District not found
        resp.raise_for_status()
        return resp.json()
    except httpx.HTTPError as e:
        logger.warning(f"Failed to fetch wiki data for {geoid}: {e}")
        return None

Response Schema Reference

WikipediaDistrictData

Field Type Description
geoid string Census GEOID (4 digits)
state_code string 2-letter state abbreviation (lowercase)
state_name string Full state name
district_number int District number (0 for at-large)
is_at_large bool Whether this is an at-large district
title string Formal district title
summary string Wikipedia summary (2-3 sentences)
population string? Population from Wikipedia
representative string? Current representative name
party string? Party: "Republican" or "Democrat"
cook_pvi string? Cook PVI (e.g., "R+5", "D+10", "EVEN")
counties string[] List of counties in district
wikipedia_url string Full Wikipedia page URL
cached_at datetime When data was cached
cache_expires_at datetime When cache expires

DistrictDetail

Field Type Description
geoid string Census GEOID
name string District name
state_fips string 2-digit state FIPS
state_name string Full state name
population int? Total population
median_age float? Median age
median_income int? Median household income
bachelors_plus int? Population with bachelor's degree or higher
unemployment_rate float? Unemployment rate (%)
median_home_value int? Median home value

Rate Limits

No rate limits currently enforced, but please: - Cache responses on your end when appropriate - Avoid polling endpoints more than once per minute - Use limit=500 for bulk fetches instead of many small requests


OpenAPI/Swagger

Interactive API documentation available at: - Swagger UI: https://districts.nominate.ai/docs - ReDoc: https://districts.nominate.ai/redoc - OpenAPI JSON: https://districts.nominate.ai/openapi.json


Contact

For API issues or feature requests, contact the cbdistricts team or file an issue in the repository.