{"openapi":"3.1.0","info":{"title":"School Record","summary":"Published admissions and inspection figures for schools in England.","description":"Read-only access to the same figures the public pages state, from official sources, with the period and caveat attached to every measure.\n\n**Per-school JSON.** The simplest entry point is not here but at `/school/{urn}.json`, which mirrors a school's page exactly.\n\n**What this does not do.** Nothing here predicts whether a child will be offered a place. Demand is not admission: a school can be heavily over-subscribed on first preferences and still admit every applicant from its catchment.\n\n**Please carry the caveats.** A progress score without its confidence interval, a category of concern without its inspection date, or a withheld figure read as zero are all wrong statements built from correct numbers. See `/methodology`.","license":{"name":"Contains public sector information licensed under the Open Government Licence v3.0","url":"https://www.nationalarchives.gov.uk/doc/open-government-licence/version/3/"},"version":"1.0.0"},"paths":{"/api/schools":{"get":{"tags":["schools"],"summary":"List Schools","description":"Schools that have a page here, newest filter first.\n\nOnly schools past the publish gate, which is the same rule the sitemap and\nthe HTML listings apply. Listing a school whose page 404s would advertise\npages that do not exist, and a consumer would have no way to tell that from\na broken site.\n\nNot every school in England: about 17,700 of nearly 52,000 have enough\nhistory to say anything useful about. /coverage says what is held.","operationId":"list_schools_api_schools_get","parameters":[{"name":"q","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Part of a school's name","title":"Q"},"description":"Part of a school's name"},{"name":"authority","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"DfE authority code, e.g. 806","examples":["806"],"title":"Authority"},"description":"DfE authority code, e.g. 806"},{"name":"phase","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"GIAS phase, e.g. primary or secondary","title":"Phase"},"description":"GIAS phase, e.g. primary or secondary"},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"per_page","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Per Page"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SchoolList"}}}},"404":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}},"description":"Not Found"},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/api/schools/{urn}":{"get":{"tags":["schools"],"summary":"Get School","description":"One school, by URN.","operationId":"get_school_api_schools__urn__get","parameters":[{"name":"urn","in":"path","required":true,"schema":{"type":"integer","description":"GIAS Unique Reference Number","examples":[117136],"title":"Urn"},"description":"GIAS Unique Reference Number"}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SchoolDetail"}}}},"404":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}},"description":"Not Found"},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/api/authorities":{"get":{"tags":["authorities"],"summary":"List Authorities","description":"Every local authority this site publishes a page for.\n\nUnpaged: there are 180 of them and the whole list is a few kilobytes.\n\n``schools`` counts pages, not schools in existence. A council with few\npages here has little published history held for it, which is a fact about\nthis site's coverage and not about the council.\n\nA boundary URL is given for every council. Where none are held it answers\nan empty collection rather than a 404, because \"we hold no zones here\" is\nthe truthful answer and a missing URL reads as a broken one. /coverage says\nwhich councils have boundaries loaded.","operationId":"list_authorities_api_authorities_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AuthorityList"}}}}}}},"/api/catchments":{"get":{"tags":["catchments"],"summary":"List Catchments","description":"Admission zones held, newest council first loaded last.\n\nBoundaries are the scarce thing this project gathers: they arrive council\nby council and cover a minority of the country. A school absent from this\nlist is a school no zone is held for, which is not the same as a school\nwith no zone, and never means an address is outside one.\n\nNo geometry in a listing. Ask /catchments/{id} for a boundary.","operationId":"list_catchments_api_catchments_get","parameters":[{"name":"authority","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"DfE authority code, e.g. 806","examples":["806"],"title":"Authority"},"description":"DfE authority code, e.g. 806"},{"name":"page","in":"query","required":false,"schema":{"type":"integer","minimum":1,"default":1,"title":"Page"}},{"name":"per_page","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"default":100,"title":"Per Page"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CatchmentList"}}}},"404":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}},"description":"Not Found"},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/api/catchments/{catchment_id}":{"get":{"tags":["catchments"],"summary":"Get Catchment","description":"One catchment area, with its boundary on request.\n\nThe boundary is opt-in. This endpoint's docstring promised one for a long\ntime and never sent it, which was the docstring being wrong rather than the\ndefault being wrong: a caller listing zones, or reading a school's, has no\nuse for polygons and should not be charged for them.\n\n``bbox`` and ``area_km2`` are always given where a polygon is held, so a\ncaller can see how big the shape is before asking for it.\n\nWhat this is not: a way to decide whether an address is inside a zone. The\nshape is smoothed for drawing, councils redraw zones, and the council's own\nanswer is the authoritative one. The caveat travels in the body and in the\nX-Boundary-Accuracy header.","operationId":"get_catchment_api_catchments__catchment_id__get","parameters":[{"name":"catchment_id","in":"path","required":true,"schema":{"type":"integer","description":"Identifier from /api/catchments","title":"Catchment Id"},"description":"Identifier from /api/catchments"},{"name":"include","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Set to \"geometry\" to receive the boundary itself","title":"Include"},"description":"Set to \"geometry\" to receive the boundary itself"},{"name":"precision","in":"query","required":false,"schema":{"type":"string","description":"How much the boundary is smoothed: display or detailed","default":"detailed","title":"Precision"},"description":"How much the boundary is smoothed: display or detailed"}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/CatchmentDetail"}}}},"404":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}},"description":"Not Found"},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/api/admissions/{urn}/{year}":{"get":{"tags":["admissions"],"summary":"Get Admissions","description":"A school's council offer-day figures, newest year first.","operationId":"get_admissions_api_admissions__urn___year__get","parameters":[{"name":"urn","in":"path","required":true,"schema":{"type":"integer","description":"GIAS Unique Reference Number","examples":[117136],"title":"Urn"},"description":"GIAS Unique Reference Number"},{"name":"year","in":"path","required":true,"schema":{"type":"integer","maximum":2100,"minimum":2000,"description":"September intake year, e.g. 2025","title":"Year"},"description":"September intake year, e.g. 2025"}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/AdmissionsResponse"}}}},"404":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}},"description":"Not Found"},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/":{"get":{"tags":["pages"],"summary":"Home","description":"The way in.\n\nWithout this the 17,244 school pages are reachable only through the sitemap,\nwhich is a weak crawl signal and no use to a person at all.","operationId":"home__get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/schools/{slug}.md":{"get":{"tags":["pages"],"summary":"Authority Markdown","description":"One council's school list as plain Markdown, at a stable URL.\n\nRegistered before \"/schools/{slug}\" so \"sheffield.md\" is not read as a\ncouncil slug. The same schools and figures the HTML listing shows, with\nnone of the page furniture.","operationId":"authority_markdown_schools__slug__md_get","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","title":"Slug"}}],"responses":{"200":{"description":"Successful Response","content":{"text/plain":{"schema":{"type":"string"}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/schools/{slug}":{"get":{"tags":["pages"],"summary":"Authority Page","description":"Every published school in one local authority.","operationId":"authority_page_schools__slug__get","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","title":"Slug"}},{"name":"page","in":"query","required":false,"schema":{"type":"integer","default":1,"title":"Page"}}],"responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/schools/{slug}/most-sought-after":{"get":{"tags":["pages"],"summary":"Authority Most Sought After","description":"One council's schools ordered by first preferences per place.\n\nRegistered before \"/schools/{slug}/{phase}\" so this exact path is not read\nas a phase filter. It answers a question people and answer engines ask in\nthese words: \"the most sought-after schools in X\". The ordering is a\npublished number and nothing more, which the page states before the list.","operationId":"authority_most_sought_after_schools__slug__most_sought_after_get","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","title":"Slug"}}],"responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/schools/{slug}/{phase}":{"get":{"tags":["pages"],"summary":"Authority Page By Phase","description":"One phase of schools in one local authority, such as /schools/kent/secondary.\n\nA separate URL rather than a query string because it is worth citing and\nworth indexing on its own: \"secondary schools in Kent\" is a question people\nand answer engines actually ask.","operationId":"authority_page_by_phase_schools__slug___phase__get","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","title":"Slug"}},{"name":"phase","in":"path","required":true,"schema":{"type":"string","title":"Phase"}},{"name":"page","in":"query","required":false,"schema":{"type":"integer","default":1,"title":"Page"}}],"responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/area/{district}.md":{"get":{"tags":["pages"],"summary":"Area Markdown","description":"One postcode district's school list as plain Markdown.\n\nRegistered before \"/area/{district}\" so \"ts8.md\" is not read as a district.","operationId":"area_markdown_area__district__md_get","parameters":[{"name":"district","in":"path","required":true,"schema":{"type":"string","title":"District"}}],"responses":{"200":{"description":"Successful Response","content":{"text/plain":{"schema":{"type":"string"}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/area/{district}":{"get":{"tags":["pages"],"summary":"Area Page","description":"Every published school in one postcode district.","operationId":"area_page_area__district__get","parameters":[{"name":"district","in":"path","required":true,"schema":{"type":"string","title":"District"}},{"name":"page","in":"query","required":false,"schema":{"type":"integer","default":1,"title":"Page"}}],"responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/area/{district}/{phase}":{"get":{"tags":["pages"],"summary":"Area Page By Phase","description":"One phase of schools in one postcode district, such as /area/ts8/secondary.","operationId":"area_page_by_phase_area__district___phase__get","parameters":[{"name":"district","in":"path","required":true,"schema":{"type":"string","title":"District"}},{"name":"phase","in":"path","required":true,"schema":{"type":"string","title":"Phase"}},{"name":"page","in":"query","required":false,"schema":{"type":"integer","default":1,"title":"Page"}}],"responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/school/{urn}.json":{"get":{"tags":["pages","schools"],"summary":"School Json","description":"The school page as JSON, at a stable URL.\n\nRegistered before the HTML routes: \"/school/{urn}\" would otherwise match\n\"134223.json\" and reject it as a malformed integer.\n\nExactly what the HTML states, built from the same object, so an agent and a\nperson cannot get different answers. Linked from the page itself so it is\ndiscoverable without documentation.","operationId":"school_json_school__urn__json_get","parameters":[{"name":"urn","in":"path","required":true,"schema":{"type":"integer","title":"Urn"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SchoolJson"}}}},"404":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}},"description":"Not Found"},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/school/{urn}.md":{"get":{"tags":["pages"],"summary":"School Markdown","description":"The school page as plain Markdown, at a stable URL.\n\nThe same facts as the HTML and the JSON, with none of the navigation,\nstyling or script an answer engine would otherwise have to read past to\nreach them. Built from the same object, so it cannot say something the page\ndoes not. Registered before the HTML routes for the same reason the JSON\ntwin is: \"/school/{urn}\" would otherwise try to parse \"134223.md\" as an int.","operationId":"school_markdown_school__urn__md_get","parameters":[{"name":"urn","in":"path","required":true,"schema":{"type":"integer","title":"Urn"}}],"responses":{"200":{"description":"Successful Response","content":{"text/plain":{"schema":{"type":"string"}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/school/{urn}/alternatives.md":{"get":{"tags":["pages"],"summary":"School Alternatives Markdown","description":"The alternatives comparison as Markdown.\n\nNo slug in the path, matching the school twin at \"/school/{urn}.md\": a twin\nis addressed by the stable identifier, and a slug in it would mean a rename\nbreaks a URL a machine has stored.","operationId":"school_alternatives_markdown_school__urn__alternatives_md_get","parameters":[{"name":"urn","in":"path","required":true,"schema":{"type":"integer","title":"Urn"}}],"responses":{"200":{"description":"Successful Response","content":{"text/plain":{"schema":{"type":"string"}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/school/{urn}":{"get":{"tags":["pages"],"summary":"School Page","description":"One school's public page.\n\nTwo routes reach this: the full URL with the name in it, and the short one\nwithout. The short one redirects, so every school has one canonical address.","operationId":"school_page_school__urn__get","parameters":[{"name":"urn","in":"path","required":true,"schema":{"type":"integer","title":"Urn"}},{"name":"slug","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Slug"}}],"responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/school/{urn}/{slug}":{"get":{"tags":["pages"],"summary":"School Page","description":"One school's public page.\n\nTwo routes reach this: the full URL with the name in it, and the short one\nwithout. The short one redirects, so every school has one canonical address.","operationId":"school_page_school__urn___slug__get","parameters":[{"name":"urn","in":"path","required":true,"schema":{"type":"integer","title":"Urn"}},{"name":"slug","in":"path","required":true,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Slug"}}],"responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/school/{urn}/{slug}/alternatives":{"get":{"tags":["pages"],"summary":"School Alternatives","description":"Nearby schools of the same phase, nearest first.\n\nOne page per school, never pairwise: 17,244 schools would be 148 million\npairs, and publishing those is how a programmatic domain gets suppressed.","operationId":"school_alternatives_school__urn___slug__alternatives_get","parameters":[{"name":"urn","in":"path","required":true,"schema":{"type":"integer","title":"Urn"}},{"name":"slug","in":"path","required":true,"schema":{"type":"string","title":"Slug"}}],"responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/search":{"get":{"tags":["pages"],"summary":"Search","description":"Search published schools by name.\n\nServer-side so it works without JavaScript. A static export would serve the\nsame results from a prebuilt index instead; the route is the live form.","operationId":"search_search_get","parameters":[{"name":"q","in":"query","required":false,"schema":{"type":"string","default":"","title":"Q"}}],"responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/find":{"get":{"tags":["pages"],"summary":"Find Form","description":"The way in for \"which schools are near where I live\".\n\nA form, indexable on its own because \"schools near <place>\" is a question\nworth a page. The result pages it leads to are not indexed: one per postcode\nwould be a million near-identical pages, and the facts on them are already\non the school pages they link to.\n\nA plain HTML form submits here with ``?postcode=``; this redirects to the\ntidy ``/find/<postcode>`` path so the result has its own address and works\nwith no JavaScript at all.","operationId":"find_form_find_get","parameters":[{"name":"postcode","in":"query","required":false,"schema":{"type":"string","default":"","title":"Postcode"}}],"responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/find/{postcode}":{"get":{"tags":["pages"],"summary":"Find Results","description":"Nearest published schools to a postcode, with the figures for each.\n\nStates facts and stops: distance from the postcode, whether the point falls\ninside a catchment the council publishes for that school (or that none is\nheld), the newest published cut-off, and how demand has moved. It never says\na child would or would not be offered a place.","operationId":"find_results_find__postcode__get","parameters":[{"name":"postcode","in":"path","required":true,"schema":{"type":"string","title":"Postcode"}}],"responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/sitemap.xml":{"get":{"tags":["pages"],"summary":"Sitemap Index","description":"The sitemap index, listing the chunked sitemaps in the order they matter.\n\nSeventeen thousand school pages exceed what one sitemap may hold, so they\nare split and this points at the parts.\n\n**The order is the argument, not presentation.** On 2026-09-19 Search\nConsole reported 2 pages indexed, 40,255 \"Discovered - currently not\nindexed\", and 11 Googlebot crawl requests in ninety days against a host\nit recorded as healthy. Google had read the sitemap, found every URL and\ndeclined to spend the budget. A new domain gets very little, and what it\ndoes get is spent from the top of the index down.\n\nSo the scarce pages go first: the schools holding a catchment boundary\nor a council's offer-day figures, which is the only part of this site\nthat cannot be got from a national download. Then the hub pages, which\ncarry the site's shape. Then the long tail. If a crawler reads eleven\nthings, those eleven should be the ones that show what the site is for.","operationId":"sitemap_index_sitemap_xml_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/sitemap-schools-scarce-{chunk}.xml":{"get":{"tags":["pages"],"summary":"Sitemap Scarce Chunk","description":"The lead tier: schools holding a catchment boundary or offer-day figures.\n\nListed first in the index, because these are the pages held nowhere else and\nthe crawl budget that reaches this site is small enough to matter. See\n``sitemap_index``.","operationId":"sitemap_scarce_chunk_sitemap_schools_scarce__chunk__xml_get","parameters":[{"name":"chunk","in":"path","required":true,"schema":{"type":"integer","title":"Chunk"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/sitemap-schools-{chunk}.xml":{"get":{"tags":["pages"],"summary":"Sitemap Chunk","description":"The tail: schools whose page carries only the national layer.","operationId":"sitemap_chunk_sitemap_schools__chunk__xml_get","parameters":[{"name":"chunk","in":"path","required":true,"schema":{"type":"integer","title":"Chunk"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/most-sought-after":{"get":{"tags":["pages"],"summary":"Most Sought After National","description":"The schools the most families named first, nationally.\n\nThe per-council version has existed for a while and is the more useful one,\nbecause a school two hundred miles away is not a choice. This exists because\nit is the first question people ask, and because a site that will not answer\nit looks like one that cannot.","operationId":"most_sought_after_national_most_sought_after_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/coverage":{"get":{"tags":["pages"],"summary":"Coverage","description":"State exactly what is held and what is not.\n\nExcluding data is only defensible while the exclusion is declared, so every\ngap the loaders know about is named here rather than left to be inferred\nfrom an absence.","operationId":"coverage_coverage_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/intake/{year}.md":{"get":{"tags":["pages"],"summary":"Intake Markdown","description":"The intake briefing as Markdown.\n\nRegistered before \"/intake/{year}\" for the same reason the school twin is:\nFastAPI would otherwise try to parse \"2026.md\" as an int and reject it.","operationId":"intake_markdown_intake__year__md_get","parameters":[{"name":"year","in":"path","required":true,"schema":{"type":"integer","title":"Year"}}],"responses":{"200":{"description":"Successful Response","content":{"text/plain":{"schema":{"type":"string"}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/intake":{"get":{"tags":["pages"],"summary":"Intake Latest","description":"The newest round held, so the masthead has a year-free address to link.\n\nEvery intake page is per-year by design, because the figures for a September\ndo not change once published and a citation that silently came to mean a\ndifferent year would be worse than no page at all. That makes a hardcoded\nnav link a 404 waiting for the next autumn. This forwards instead, and 302\nrather than 301 because which year is newest is exactly the thing that moves.","operationId":"intake_latest_intake_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/intake/{year}":{"get":{"tags":["pages"],"summary":"Intake Page","description":"How one admissions round turned out across England.\n\nA page per intake year rather than one page that always describes the newest\nround. The figures for a given September do not change after they are\npublished, so each year is a stable thing to cite, and a citation that\nsilently came to mean a different year would be worse than no page at all.\n\nEverything on it is computed from the year asked for, so last June's page and\nnext June's are both right without an edit.\n\nA year with no figures 404s rather than rendering a page of blanks, which is\nthe same rule the school publish gate follows.","operationId":"intake_page_intake__year__get","parameters":[{"name":"year","in":"path","required":true,"schema":{"type":"integer","title":"Year"}}],"responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/places/{year}.md":{"get":{"tags":["pages"],"summary":"Places Markdown","description":"The places briefing as Markdown.\n\nRegistered before \"/places/{year}\" for the same reason the intake twin is:\nFastAPI would otherwise try to parse \"2024.md\" as an int and reject it.","operationId":"places_markdown_places__year__md_get","parameters":[{"name":"year","in":"path","required":true,"schema":{"type":"integer","title":"Year"}}],"responses":{"200":{"description":"Successful Response","content":{"text/plain":{"schema":{"type":"string"}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/places":{"get":{"tags":["pages"],"summary":"Places Latest","description":"The newest collection held, so the masthead has a year-free address.\n\n302 and not 301, because which year is newest is exactly the thing that\nmoves. The same reasoning as /intake, and for the same reason: a hardcoded\nnav link is a 404 waiting for the next autumn.","operationId":"places_latest_places_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/places/{year}":{"get":{"tags":["pages"],"summary":"Places Page","description":"How many school places England had in one year, and how many were empty.\n\nA page per academic year rather than one page that always describes the\nnewest collection, for the reason the intake page gives: the figures for a\ngiven year do not change once published, so each year is a stable thing to\ncite, and a citation that silently came to mean a different year would be\nworse than no page at all.\n\nA year with no collection 404s rather than rendering blanks. 2019 is such a\nyear: the Department did not run it, and a page of noughts would say the\nschools had vanished.","operationId":"places_page_places__year__get","parameters":[{"name":"year","in":"path","required":true,"schema":{"type":"integer","title":"Year"}}],"responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/sitemap-index-pages.xml":{"get":{"tags":["pages"],"summary":"Sitemap Index Pages","description":"The homepage, coverage, and every authority and area listing.","operationId":"sitemap_index_pages_sitemap_index_pages_xml_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/map":{"get":{"tags":["pages"],"summary":"National Map","description":"A map of England showing every council we publish schools for.\n\nThe map is a picture of the same information the list underneath it carries,\nso the page works with scripts switched off and a crawler reads every\nauthority as a plain link.","operationId":"national_map_map_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/data/authorities.geojson":{"get":{"tags":["pages"],"summary":"Authorities Geojson","description":"Council outlines with school and catchment counts, as GeoJSON.\n\nFetched by the map on /map, and useful on its own to anyone who wants to\ndraw their own. The outlines come from the Office for National Statistics\nunder the Open Government Licence and are simplified for drawing, so they\nmust not be used to decide whether an address falls inside an area.","operationId":"authorities_geojson_data_authorities_geojson_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/data/catchments/{slug}.geojson":{"get":{"tags":["pages"],"summary":"Authority Catchments Geojson","description":"Every catchment boundary in one council, as GeoJSON.\n\nFetched by the map when a reader looks at a council, and useful on its own to\nanyone drawing their own map of an area.\n\nBoundaries are simplified to about 80 metres for this view. That is coarse\non purpose: it is for seeing the shape of an area, not for deciding which\nside of a line a house sits on. The school page draws the same boundary at\nabout 20 metres, and even that is not precise enough for a single address.","operationId":"authority_catchments_geojson_data_catchments__slug__geojson_get","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","title":"Slug"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/data/schools/{slug}.geojson":{"get":{"tags":["pages"],"summary":"Authority School Points Geojson","description":"Every published school in one council, as GeoJSON points.\n\nFetched by /map when a reader zooms into a council, and useful on its own to\nanyone plotting the schools of an area. Each point links to the school's\npage; it carries no figures, because a dot on a map is a way to the page,\nnot a place to read facts off.","operationId":"authority_school_points_geojson_data_schools__slug__geojson_get","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","title":"Slug"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"400":{"description":"Bad request: a parameter or body field is not valid","content":{"application/json":{"schema":{"$ref":"#/components/schemas/ErrorResponse"}}}}}}},"/methodology":{"get":{"tags":["pages"],"summary":"Methodology","description":"What is comparable between schools and what is not.\n\nLocal authorities genuinely differ, so a single universal standard is not\navailable for everything. Where one exists we apply it; where it does not we\nname the authority and publish what it published. Saying which is which is\nthe only honest alternative to pretending the difference is not there.","operationId":"methodology_methodology_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/about":{"get":{"tags":["pages"],"summary":"About","description":"Who publishes this site, and how to reach them.\n\nThe footer carried a note for a while saying this page was the thing the\nsite was missing: ONS releases name a statistician, Locrating names a\ncompany, and this named neither, so a reader who wanted to challenge a\nfigure had \"Report an error\" and nothing to attach it to.\n\nIt names the project rather than a person, which is a deliberate choice and\none the page states in its own words rather than leaving a reader to\nnotice. What stands in for a byline here is the source trail: every figure\nsays where it came from and when, so the site can be checked instead of\ntrusted. That is the stronger claim of the two, and it is the one that is\nactually true of this site.","operationId":"about_about_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/corrections":{"get":{"tags":["pages"],"summary":"Corrections","description":"How to tell us something is wrong.\n\nLinked from every page. Publishing facts about named institutions without a\nroute to challenge them would be indefensible, and a correction from someone\nwho knows the school is the cheapest quality signal available.","operationId":"corrections_corrections_get","responses":{"200":{"description":"Successful Response","content":{"text/html":{"schema":{"type":"string"}}}}}}},"/robots.txt":{"get":{"tags":["pages"],"summary":"Robots","description":"robots.txt. Admits AI crawlers deliberately: being read is the point.","operationId":"robots_robots_txt_get","responses":{"200":{"description":"Successful Response","content":{"text/plain":{"schema":{"type":"string"}}}}}}},"/llms.txt":{"get":{"tags":["pages"],"summary":"Llms Txt","description":"llms.txt: what this site holds and what its measures mean.\n\nWritten for an answer engine rather than a crawler. A model that repeats a\nlimitation correctly is worth more than one that repeats a number.","operationId":"llms_txt_llms_txt_get","responses":{"200":{"description":"Successful Response","content":{"text/plain":{"schema":{"type":"string"}}}}}}},"/api":{"get":{"tags":["meta"],"summary":"Api Info","description":"What this service is and where its documentation lives.\n\nLives at /api because / is the public homepage. It used to be at /.","operationId":"api_info_api_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/health":{"get":{"tags":["meta"],"summary":"Health","description":"Is the service up, and can it reach its database?\n\nReturns 503 when the database is unreachable, so a load balancer stops\nsending traffic to a machine that can only serve errors.","operationId":"health_health_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HealthResponse"}}}},"503":{"description":"Service Unavailable","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HealthResponse"}}}}}}}},"components":{"schemas":{"AdmissionsRecord":{"properties":{"entry_point":{"type":"string","title":"Entry Point"},"pan":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Pan"},"applications_total":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Applications Total"},"applications_basis":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Applications Basis"},"first_preferences":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"First Preferences"},"offers_total":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Offers Total"},"oversubscribed":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Oversubscribed"},"last_criterion":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Criterion"},"furthest_distance_m":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Furthest Distance M"},"distance_measure":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Distance Measure"},"waiting_list_size":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Waiting List Size"},"notes":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Notes"},"source_document":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Document"},"source_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Url"}},"type":"object","required":["entry_point"],"title":"AdmissionsRecord","description":"One school's admissions figures for one intake year.\n\nPublished by a local authority on national offer day. Only a few councils\npublish these, which is why the field that says how far the last offer\nreached is the scarcest thing this project holds."},"AdmissionsResponse":{"properties":{"urn":{"type":"integer","title":"Urn"},"school_name":{"type":"string","title":"School Name"},"intake_year":{"type":"integer","title":"Intake Year"},"results":{"items":{"$ref":"#/components/schemas/AdmissionsRecord"},"type":"array","title":"Results"}},"type":"object","required":["urn","school_name","intake_year","results"],"title":"AdmissionsResponse","description":"A school's admissions history, newest year first."},"AuthorityList":{"properties":{"total":{"type":"integer","title":"Total"},"results":{"items":{"$ref":"#/components/schemas/AuthorityListItem"},"type":"array","title":"Results"}},"type":"object","required":["total","results"],"title":"AuthorityList","description":"Every authority with a page. Small and unpaged: there are 180 of them."},"AuthorityListItem":{"properties":{"authority_id":{"type":"string","title":"Authority Id"},"name":{"type":"string","title":"Name"},"slug":{"type":"string","title":"Slug"},"schools":{"type":"integer","title":"Schools"},"url":{"type":"string","title":"Url"},"catchments_geojson_url":{"type":"string","title":"Catchments Geojson Url"},"schools_geojson_url":{"type":"string","title":"Schools Geojson Url"}},"type":"object","required":["authority_id","name","slug","schools","url","catchments_geojson_url","schools_geojson_url"],"title":"AuthorityListItem","description":"One local authority, and the addresses that resolve for it."},"CatchmentDetail":{"properties":{"catchment_id":{"type":"integer","title":"Catchment Id"},"authority_id":{"type":"string","title":"Authority Id"},"area_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Area Name"},"category":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Category"},"phase":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phase"},"is_denominational":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Denominational"},"intake_year_from":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Intake Year From"},"intake_year_to":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Intake Year To"},"source_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Url"},"metadata_version":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Metadata Version"},"school":{"anyOf":[{"$ref":"#/components/schemas/CatchmentSchoolRef"},{"type":"null"}]},"geometry_available":{"type":"boolean","title":"Geometry Available","default":false},"geometry_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Geometry Url"},"bbox":{"anyOf":[{"items":{"type":"number"},"type":"array"},{"type":"null"}],"title":"Bbox"},"area_km2":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Area Km2"},"boundary_accuracy":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Boundary Accuracy"},"geometry":{"anyOf":[{"additionalProperties":true,"type":"object"},{"type":"null"}],"title":"Geometry"}},"type":"object","required":["catchment_id","authority_id"],"title":"CatchmentDetail","description":"One catchment area in full, including its boundary as GeoJSON."},"CatchmentList":{"properties":{"total":{"type":"integer","title":"Total"},"page":{"type":"integer","title":"Page"},"per_page":{"type":"integer","title":"Per Page"},"total_pages":{"type":"integer","title":"Total Pages"},"results":{"items":{"$ref":"#/components/schemas/CatchmentListItem"},"type":"array","title":"Results"}},"type":"object","required":["total","page","per_page","total_pages","results"],"title":"CatchmentList","description":"A page of catchment areas."},"CatchmentListItem":{"properties":{"catchment_id":{"type":"integer","title":"Catchment Id"},"authority_id":{"type":"string","title":"Authority Id"},"area_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Area Name"},"category":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Category"},"phase":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phase"},"school_urn":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"School Urn"},"url":{"type":"string","title":"Url"}},"type":"object","required":["catchment_id","authority_id","url"],"title":"CatchmentListItem","description":"One catchment area in a listing, without its geometry.\n\nNo polygon here for the reason CatchmentSummary gives: a page of them would\nbe megabytes. Ask the detail endpoint for a boundary."},"CatchmentSchoolRef":{"properties":{"school_id":{"type":"integer","title":"School Id"},"urn":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Urn"},"name":{"type":"string","title":"Name"}},"type":"object","required":["school_id","name"],"title":"CatchmentSchoolRef","description":"A pointer from a catchment area to the school it belongs to."},"CatchmentSummary":{"properties":{"catchment_id":{"type":"integer","title":"Catchment Id"},"category":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Category"},"phase":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phase"},"is_denominational":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Is Denominational"},"area_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Area Name"},"intake_year_from":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Intake Year From"},"intake_year_to":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Intake Year To"}},"type":"object","required":["catchment_id"],"title":"CatchmentSummary","description":"One catchment area, as the JSON API returns it alongside a school.\n\nCarries no geometry. A caller that wants the boundary asks the catchments\nendpoint for it, so a list of schools does not drag megabytes of polygons\nbehind it."},"ErrorResponse":{"properties":{"detail":{"type":"string","title":"Detail"},"errors":{"anyOf":[{"items":{"$ref":"#/components/schemas/FieldError"},"type":"array"},{"type":"null"}],"title":"Errors"}},"type":"object","required":["detail"],"title":"ErrorResponse","description":"A failure, described in one sentence.\n\n``detail`` is always a string. It was not: the validation handler put\npydantic's raw error list in the same field, so a client that did anything\nwith ``detail`` got a sentence from one endpoint and a list of dictionaries\nfrom another, and the declared model described only the first. The\nper-field detail now has a field of its own."},"FieldError":{"properties":{"field":{"type":"string","title":"Field"},"message":{"type":"string","title":"Message"},"type":{"type":"string","title":"Type"}},"type":"object","required":["field","message","type"],"title":"FieldError","description":"One thing wrong with a request, and where."},"HealthResponse":{"properties":{"status":{"type":"string","enum":["ok","degraded"],"title":"Status"},"database":{"type":"string","enum":["up","down"],"title":"Database"}},"type":"object","required":["status","database"],"title":"HealthResponse","description":"Whether the service is up and whether it can reach its database."},"SchoolDetail":{"properties":{"school_id":{"type":"integer","title":"School Id"},"urn":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Urn"},"seed_code":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Seed Code"},"laestab":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Laestab"},"name":{"type":"string","title":"Name"},"phase":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phase"},"type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Type"},"denomination":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Denomination"},"gender":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Gender"},"age_low":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Age Low"},"age_high":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Age High"},"admissions_policy":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Admissions Policy"},"school_capacity":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"School Capacity"},"address_line1":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Address Line1"},"town":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Town"},"postcode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Postcode"},"lat":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Lat"},"lon":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Lon"},"is_open":{"type":"boolean","title":"Is Open"},"predecessor_urn":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Predecessor Urn"},"authority_id":{"type":"string","title":"Authority Id"},"authority_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authority Name"},"catchment_ids":{"items":{"type":"integer"},"type":"array","title":"Catchment Ids"},"catchments":{"items":{"$ref":"#/components/schemas/CatchmentSummary"},"type":"array","title":"Catchments"}},"type":"object","required":["school_id","name","is_open","authority_id"],"title":"SchoolDetail","description":"Everything the JSON API knows about one school.\n\nAlmost every field is optional because the source, GIAS, leaves almost every\nfield blank for some school somewhere. None means \"not published\", never\nzero and never false."},"SchoolJson":{"properties":{"url":{"type":"string","title":"Url"},"urn":{"type":"integer","title":"Urn"},"name":{"type":"string","title":"Name"},"phase":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phase"},"type":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Type"},"local_authority":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Local Authority"},"address":{"additionalProperties":true,"type":"object","title":"Address"},"catchment":{"additionalProperties":true,"type":"object","title":"Catchment"},"ofsted":{"additionalProperties":true,"type":"object","title":"Ofsted"},"demand":{"additionalProperties":true,"type":"object","title":"Demand"},"results":{"additionalProperties":true,"type":"object","title":"Results"},"workforce":{"additionalProperties":true,"type":"object","title":"Workforce"},"sources":{"items":{},"type":"array","title":"Sources"}},"additionalProperties":true,"type":"object","required":["url","urn","name","address","catchment","ofsted","demand","results","workforce","sources"],"title":"SchoolJson","description":"The school page as JSON: /school/{urn}.json, the page's exact twin.\n\nThis is the simplest way into the data and the one llms.txt links, so it is\nthe endpoint most likely to be built on. It returned an untyped dict and\nwas documented under \"pages\" alongside the HTML, which meant the most-used\nmachine endpoint on the site was the one with no contract at all.\n\n**A stable core, not a closed shape.** ``extra=\"allow\"``: the named fields\nbelow will not be removed or retyped without the deprecation policy in\ndocs/api.md, and fields may be added at any time. The page grows a section\nevery few weeks and a consumer that breaks on a new key would break\nconstantly.\n\n**Declared, not enforced.** It is attached with ``responses=``, not as a\n``response_model``, on purpose. FastAPI would then validate and re-serialise\na wide dict on every request to the busiest machine endpoint here, and any\ndrift between the model and what builds the dict would surface as a\nproduction 500 rather than a test failure. tests/api/test_school_json.py\ndoes the enforcing, which is where a mismatch should be found.\n\n**Carry the caveats.** Most sections have a ``note``. Those notes are the\nconditions that make the numbers true statements, and dropping them turns a\ncorrect figure into a wrong claim."},"SchoolList":{"properties":{"total":{"type":"integer","title":"Total"},"page":{"type":"integer","title":"Page"},"per_page":{"type":"integer","title":"Per Page"},"total_pages":{"type":"integer","title":"Total Pages"},"results":{"items":{"$ref":"#/components/schemas/SchoolListItem"},"type":"array","title":"Results"}},"type":"object","required":["total","page","per_page","total_pages","results"],"title":"SchoolList","description":"A page of published schools."},"SchoolListItem":{"properties":{"urn":{"type":"integer","title":"Urn"},"name":{"type":"string","title":"Name"},"slug":{"type":"string","title":"Slug"},"phase":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Phase"},"postcode":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Postcode"},"authority_id":{"type":"string","title":"Authority Id"},"authority_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Authority Name"},"url":{"type":"string","title":"Url"},"json_url":{"type":"string","title":"Json Url"}},"type":"object","required":["urn","name","slug","authority_id","url","json_url"],"title":"SchoolListItem","description":"One school in a listing: who it is and where to read about it.\n\nDeliberately thin. A listing exists to hand out stable addresses, not to be\nsomewhere figures can be read off in bulk, and a list of measures is the\nexact shape that invites sorting into a league table. The same reasoning is\nalready written into the school points the map draws from: a dot is a way\nto the page, not a place to read facts off."}}},"tags":[{"name":"schools","description":"One school's identity and the catchment areas it is linked to. Identity comes from GIAS and is national and complete. A school being here says nothing about how contested it is."},{"name":"catchments","description":"An admission zone as a council drew it. Held for a minority of councils, so the absence of a zone for a school means only that none is held, never that an address falls outside one."},{"name":"admissions","description":"A council's own offer-day figures: places, applications, and how far the last offer reached. Published by only a few councils, and a record of what happened in one year. Nothing here predicts whether a child will be offered a place."},{"name":"authorities","description":"The councils with a page here, and the addresses that resolve for each. The entry point for working council by council. A council's school count is a count of pages held, not of schools in existence, and not every council has one."},{"name":"pages","description":"Public HTML pages and the per-school JSON."},{"name":"meta","description":"Service description and health."}]}