{"openapi":"3.1.0","info":{"title":"Blueflo Building Health API","summary":"What public records say about a New York City building.","description":"Every value carries its source and an as-of date. Cards report what city records say — they are not inspections, they carry no warranty, and they may not be used for tenant screening. Individuals are never named; companies are. Apartments appear only where a city record names one.\n\nHow to answer a question about a building: turn the address, or a listing URL, into a `slug` with `find_building`, then read `building_overview` — one status per system, which answers most questions. Go deeper with `building_topic` for one topic, `apartment` for one apartment, and `records` or `record` for the evidence. Use `find_buildings_where` for questions across buildings, such as an owner's other buildings.\n\nQuote `status`, `display` and `sentence` as written: the wording is the claim the records support. Null means unknown, never fine — read the note beside it, such as `comparison_note`. A 404 for a building means it is not indexed yet, not that it is clean. Link the `page` of whatever you quote.","version":"0.1.0"},"paths":{"/healthz":{"get":{"tags":["meta"],"summary":"Liveness, and how old the data is","description":"Whether the service is up and can read its cards, how many the index lists, and when the nightly job last checked any source. Answers 503 once that is older than BLUEFLO_NIGHT_MAX_AGE_HOURS. Served at /health in production: Cloud Run answers /healthz itself.","operationId":"health","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Health"}}}}},"x-mcp":false,"x-mcp-why":"An operator's liveness check; it says nothing about any building."}},"/v1/events":{"post":{"tags":["meta"],"summary":"Report a page event — this is how a share is counted","description":"Count one page event, such as a share. Send an allowed `event` name and, optionally, the building's `slug`. An unknown name is refused with 422 and the allowed list. The sender is counted once a day by a one-way code deleted at the end of the day; no cookie, and nothing that identifies them is kept.","operationId":"record_event","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/EventIn"}}},"required":true},"responses":{"204":{"description":"Successful Response"},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/v1/sources":{"get":{"tags":["meta"],"summary":"Every dataset a card can draw on","description":"Every dataset a card can draw on: its key, name, agency and dataset id. Every fact on a card names one of these keys in its `source` field.","operationId":"list_sources","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SourceList"}}}}},"x-mcp":false,"x-mcp-why":"Every fact already names its `source`; the full dataset list is reference for developers."}},"/v1/search":{"get":{"tags":["buildings"],"summary":"Find a building by partial address","description":"Find buildings by part of an address that includes a house number, such as '126 macdou', or by a StreetEasy, Zillow or Apartments.com listing URL. A URL is read for the address it spells out and is never fetched; it searches only the borough it names. A URL that carries only a listing ID returns no results, so ask for the address. Returns each match's `slug` and whether it is indexed. Each building appears once, however the city spells it. When several boroughs match, all are returned and nothing is guessed. `indexed: false` means not covered yet, which is not the same as clean. Pass an indexed slug to `building_overview`.","operationId":"find_building","parameters":[{"name":"q","in":"query","required":true,"schema":{"type":"string","minLength":3,"description":"Part of an address, at least 3 characters. A house number is required for a match — '126 macdou', not 'macdougal'. Or a listing URL, such as https://streeteasy.com/building/10-east-10-street-new_york.","examples":["126 macdou"],"title":"Q"},"description":"Part of an address, at least 3 characters. A house number is required for a match — '126 macdou', not 'macdougal'. Or a listing URL, such as https://streeteasy.com/building/10-east-10-street-new_york."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":20,"minimum":1,"description":"Maximum matches to return.","default":8,"title":"Limit"},"description":"Maximum matches to return."}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SearchResults"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/v1/coverage":{"get":{"tags":["meta"],"summary":"What is indexed","description":"How many buildings are indexed, by borough, and their slugs, paged. A building outside coverage returns 404 from get_building.","operationId":"get_coverage","parameters":[{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":1000,"minimum":1,"description":"Maximum slugs to return.","default":200,"title":"Limit"},"description":"Maximum slugs to return."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Skip this many slugs, to page through.","default":0,"title":"Offset"},"description":"Skip this many slugs, to page through."}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Coverage"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-mcp":false,"x-mcp-why":"Pages of slugs are no use to a model; `find_buildings_where` says how many buildings it searched."}},"/v1/buildings/{slug}":{"get":{"tags":["buildings"],"summary":"A card by its slug","description":"Everything a card says about one building: identity, headline, basics, every fact by section with its source and dates, the agency records, the owner companies, and what was withheld as not re-checked. About 30 KB; for a single question prefer building_overview, building_topic, records or apartment.","operationId":"get_building","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"The building's stable id here, derived from its address of record. Get one from `find_building`, or from `find_buildings_where`.","title":"Slug"},"description":"The building's stable id here, derived from its address of record. Get one from `find_building`, or from `find_buildings_where`."}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Card"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-mcp":false,"x-mcp-why":"The whole card, up to 1.8 MB, would fill an agent's context; `building_overview` and its drill-downs answer the same questions in a few KB."}},"/v1/buildings":{"get":{"tags":["buildings"],"summary":"A card by address","description":"The same card as get_building, looked up by street address and borough instead of slug. 404 when the building is not indexed; 409 when the address matches more than one building.","operationId":"get_building_by_address","parameters":[{"name":"address","in":"query","required":true,"schema":{"type":"string","minLength":3,"description":"A full street address with a house number. Resolved through the city geocoder, so this endpoint is rate-limited more tightly than the rest — prefer a slug when you have one.","examples":["126 MacDougal St"],"title":"Address"},"description":"A full street address with a house number. Resolved through the city geocoder, so this endpoint is rate-limited more tightly than the rest — prefer a slug when you have one."},{"name":"borough","in":"query","required":true,"schema":{"type":"string","description":"Manhattan, Bronx, Brooklyn, Queens, Staten Island","title":"Borough"},"description":"Manhattan, Bronx, Brooklyn, Queens, Staten Island"},{"name":"build_if_missing","in":"query","required":false,"schema":{"type":"boolean","description":"Build the card if it is not indexed yet. Costs ~99 s; off unless BUILD_ON_MISS=1","title":"Build If Missing"},"description":"Build the card if it is not indexed yet. Costs ~99 s; off unless BUILD_ON_MISS=1"}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/Card"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-mcp":false,"x-mcp-why":"`find_building` then `building_overview` does the same, without spending the geocoder's tighter budget on every call."}},"/v1/buildings/{slug}/systems":{"get":{"tags":["buildings"],"summary":"A building's systems, with each one's status","description":"The overview, and the place to start: one building's headline, each system's status in a sentence a resident would understand (with how it compares to similar buildings nearby), how many records of each kind it has, and how many apartments those records name. Answers 'is this building okay?' in one call.","operationId":"building_overview","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"The building's stable id here, derived from its address of record. Get one from `find_building`, or from `find_buildings_where`.","title":"Slug"},"description":"The building's stable id here, derived from its address of record. Get one from `find_building`, or from `find_buildings_where`."}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SystemList"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/v1/buildings/{slug}/systems/{key}":{"get":{"tags":["buildings"],"summary":"One system: its status and every record behind it","description":"One system's status for one building, and every fact and record behind it. Use it for a question such as 'are there pests?' or 'did the boiler pass inspection?'.","operationId":"building_topic","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"The building's stable id here, derived from its address of record. Get one from `find_building`, or from `find_buildings_where`.","title":"Slug"},"description":"The building's stable id here, derived from its address of record. Get one from `find_building`, or from `find_buildings_where`."},{"name":"key","in":"path","required":true,"schema":{"type":"string","description":"System id, as `building_overview` lists it: heat, water, pests, safety, electrical, gas, elevators, envelope, flood, renting, energy, other.","title":"Key"},"description":"System id, as `building_overview` lists it: heat, water, pests, safety, electrical, gas, elevators, envelope, flood, renting, energy, other."}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/SystemDetail"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/v1/index":{"get":{"tags":["buildings"],"summary":"Search across indexed buildings","description":"Search indexed buildings by what their records say: borough, ZIP, owner company, a system's status, headline tier, year built, or a map box. Paged; `searched` and `matched` say how many buildings were considered and how many matched.","operationId":"find_buildings_where","parameters":[{"name":"borough","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Manhattan, Bronx, Brooklyn, Queens, Staten Island","title":"Borough"},"description":"Manhattan, Bronx, Brooklyn, Queens, Staten Island"},{"name":"zip","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"ZIP code","title":"Zip"},"description":"ZIP code"},{"name":"owner","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Owner name, partial match. Companies only","title":"Owner"},"description":"Owner name, partial match. Companies only"},{"name":"system","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"One of heat, water, pests, safety, electrical, gas, elevators, envelope, flood, renting, energy, other. Alone, it finds buildings whose status for it begins 'Issues on record': something the city found and has not closed. Results then carry only that system's status.","title":"System"},"description":"One of heat, water, pests, safety, electrical, gas, elevators, envelope, flood, renting, energy, other. Alone, it finds buildings whose status for it begins 'Issues on record': something the city found and has not closed. Results then carry only that system's status."},{"name":"status","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"With `system`: how its status begins, such as 'Older records on file' or 'No issues on record'.","title":"Status"},"description":"With `system`: how its status begins, such as 'Older records on file' or 'No issues on record'."},{"name":"tier","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"alert, notable, reassurance","title":"Tier"},"description":"alert, notable, reassurance"},{"name":"bbox","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"south,west,north,east in lat/lng","title":"Bbox"},"description":"south,west,north,east in lat/lng"},{"name":"built_before","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Only buildings built before this year, from PLUTO.","title":"Built Before"},"description":"Only buildings built before this year, from PLUTO."},{"name":"built_after","in":"query","required":false,"schema":{"anyOf":[{"type":"integer"},{"type":"null"}],"description":"Only buildings built after this year, from PLUTO.","title":"Built After"},"description":"Only buildings built after this year, from PLUTO."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":500,"minimum":1,"description":"Maximum buildings to return.","default":50,"title":"Limit"},"description":"Maximum buildings to return."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Skip this many results, to page through matches.","default":0,"title":"Offset"},"description":"Skip this many results, to page through matches."}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/IndexResults"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/v1/buildings/{slug}/units":{"get":{"tags":["buildings"],"summary":"Apartments named in this building's city records","description":"The apartments named in this building's city records, with how many records name each. Most apartments are named in none; `coverage` says how much of the building that is.","operationId":"list_units","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"The building's stable id here, derived from its address of record. Get one from `find_building`, or from `find_buildings_where`.","title":"Slug"},"description":"The building's stable id here, derived from its address of record. Get one from `find_building`, or from `find_buildings_where`."}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/UnitList"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}},"x-mcp":false,"x-mcp-why":"`apartment` answers 'is my apartment named?' directly, and `building_overview` says how many apartments the records name."}},"/v1/buildings/{slug}/units/{unit}":{"get":{"tags":["buildings"],"summary":"One apartment, and the city records that name it","description":"The city records that name one apartment: topic, date, class, whether closed, and where to read each. An apartment nobody filed anything about returns 200 with `known: false`, not 404. These records are about an apartment, never the people in it, and may not be used to screen a tenant.","operationId":"apartment","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"The building's stable id here, derived from its address of record. Get one from `find_building`, or from `find_buildings_where`.","title":"Slug"},"description":"The building's stable id here, derived from its address of record. Get one from `find_building`, or from `find_buildings_where`."},{"name":"unit","in":"path","required":true,"schema":{"type":"string","description":"The apartment label, as the city writes it or close to it: 4, 4R, PH, 12B. Resolved to the city's own spelling in the response.","title":"Unit"},"description":"The apartment label, as the city writes it or close to it: 4, 4R, PH, 12B. Resolved to the city's own spelling in the response."}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/UnitDetail"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/v1/buildings/{slug}/records":{"get":{"tags":["buildings"],"summary":"Every record this card carries, by kind","description":"The agency records a card carries, by type (HPD violations, DOB violations, permits, complaints), with each type's columns named. Newest first within each type, by the date it was inspected, received or issued, so the first record is the latest. Paged per type; narrow to one type with `kind`.","operationId":"records","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"The building's stable id here, derived from its address of record. Get one from `find_building`, or from `find_buildings_where`.","title":"Slug"},"description":"The building's stable id here, derived from its address of record. Get one from `find_building`, or from `find_buildings_where`."},{"name":"kind","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Narrow to one record type: complaint_patterns, dob_violations, hpd_violations, permits.","title":"Kind"},"description":"Narrow to one record type: complaint_patterns, dob_violations, hpd_violations, permits."},{"name":"limit","in":"query","required":false,"schema":{"type":"integer","maximum":1000,"minimum":1,"description":"Maximum records per kind.","default":200,"title":"Limit"},"description":"Maximum records per kind."},{"name":"offset","in":"query","required":false,"schema":{"type":"integer","minimum":0,"description":"Skip this many records per kind. Use with `has_more` to walk. Newest first, and stable.","default":0,"title":"Offset"},"description":"Skip this many records per kind. Use with `has_more` to walk. Newest first, and stable."}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/RecordSlice"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/v1/buildings/{slug}/records/{kind}/{record_id}":{"get":{"tags":["buildings"],"summary":"One record, by its id at the agency","description":"One agency record by the agency's own id: its columns, where to read it here and at the agency, and for a permit the other permits of its job. Fetched live from the city when the card does not hold it.","operationId":"record","parameters":[{"name":"slug","in":"path","required":true,"schema":{"type":"string","description":"The building's stable id here, derived from its address of record. Get one from `find_building`, or from `find_buildings_where`.","title":"Slug"},"description":"The building's stable id here, derived from its address of record. Get one from `find_building`, or from `find_buildings_where`."},{"name":"kind","in":"path","required":true,"schema":{"type":"string","description":"The record type: complaint_patterns, dob_violations, hpd_violations, permits.","title":"Kind"},"description":"The record type: complaint_patterns, dob_violations, hpd_violations, permits."},{"name":"record_id","in":"path","required":true,"schema":{"type":"string","description":"The agency's own id for the record. May contain a slash, which is why it is the final part of the path.","title":"Record Id"},"description":"The agency's own id for the record. May contain a slash, which is why it is the final part of the path."},{"name":"dataset","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"description":"Which dataset the record is in, where a kind spans several (dob_violations: ecb, bis, safety; permits: dobnow_permits, bis_permits). Omit for kinds with one dataset.","title":"Dataset"},"description":"Which dataset the record is in, where a kind spans several (dob_violations: ecb, bis, safety; permits: dobnow_permits, bis_permits). Omit for kinds with one dataset."}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"$ref":"#/components/schemas/RecordDetail"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}}},"components":{"schemas":{"Apartments":{"properties":{"named":{"type":"integer","title":"Named","description":"How many apartments city records name. Most apartments are named in none."},"in_building":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"In Building","description":"How many apartments the building has, or null where the city does not say."},"coverage":{"type":"string","title":"Coverage","description":"That comparison as a sentence."}},"type":"object","required":["named","in_building","coverage"],"title":"Apartments"},"AreaFact":{"properties":{"geography":{"type":"string","title":"Geography","description":"What the area is, such as a census tract."},"geo_value":{"type":"string","title":"Geo Value","description":"Which one."},"kind":{"type":"string","title":"Kind","description":"The fact kind, such as `flood_claims`."},"value":{"$ref":"#/components/schemas/AreaValue","description":"The numbers."},"as_of":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"As Of","description":"When the agency last updated it."},"source":{"type":"string","title":"Source","description":"The dataset key."},"source_name":{"type":"string","title":"Source Name","description":"That dataset's published title."}},"additionalProperties":true,"type":"object","required":["geography","geo_value","kind","value","as_of","source","source_name"],"title":"AreaFact","description":"A fact about the surrounding area, never about this address."},"AreaValue":{"properties":{"claims":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Claims","description":"Flood-insurance claims in the area."},"since":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Since","description":"The first year counted."},"in_2012":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"In 2012","description":"Of those, claims from 2012 (Sandy)."},"definition":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Definition","description":"What is counted."}},"additionalProperties":true,"type":"object","title":"AreaValue"},"BasicFact":{"properties":{"value":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Value","description":"The number."},"scope":{"type":"string","title":"Scope","description":"`building` or `lot` (shared with other buildings)."},"source":{"type":"string","title":"Source","description":"The dataset key."},"source_name":{"type":"string","title":"Source Name","description":"That dataset's published title."},"as_of":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"As Of","description":"When the agency last updated it."},"conflicts":{"items":{"$ref":"#/components/schemas/Conflict"},"type":"array","title":"Conflicts","description":"Other sources that give a different number."}},"additionalProperties":true,"type":"object","required":["value","scope","source","source_name","as_of"],"title":"BasicFact"},"Basics":{"properties":{"year_built":{"anyOf":[{"$ref":"#/components/schemas/BasicFact"},{"type":"null"}],"description":"Year built, from PLUTO."},"units":{"anyOf":[{"$ref":"#/components/schemas/BasicFact"},{"type":"null"}],"description":"Residential units."},"stories":{"anyOf":[{"$ref":"#/components/schemas/BasicFact"},{"type":"null"}],"description":"Stories above ground."}},"additionalProperties":true,"type":"object","title":"Basics","description":"Year built, stories and residential units, each with its source."},"BuildStats":{"properties":{"headline_tier":{"type":"string","title":"Headline Tier","description":"`alert` or `reassurance`, as the headline."},"headline_found":{"type":"boolean","title":"Headline Found","description":"Whether any headline rule matched."},"sections_found":{"type":"integer","title":"Sections Found","description":"Facts with a finding."},"sections_not_required":{"type":"integer","title":"Sections Not Required","description":"Facts that do not apply to this building."},"sections_no_record":{"type":"integer","title":"Sections No Record","description":"Facts the city has nothing for."},"sections_not_loaded":{"type":"integer","title":"Sections Not Loaded","description":"Facts whose source could not be read."},"seconds":{"type":"number","title":"Seconds","description":"How long the build took."}},"additionalProperties":true,"type":"object","required":["headline_tier","headline_found","sections_found","sections_not_required","sections_no_record","sections_not_loaded","seconds"],"title":"BuildStats","description":"How a card's build went: bookkeeping about the build, not about the building."},"BuildingMatch":{"properties":{"slug":{"type":"string","title":"Slug","description":"The one stable id for this building here. Derived from the address of record, never from what was typed, so one building has exactly one slug.","examples":["126-mac-dougal-street-manhattan"]},"label":{"type":"string","title":"Label","description":"The geocoder's full label, borough and ZIP included."},"address":{"type":"string","title":"Address","description":"House number and street, the geocoder's spelling."},"borough":{"type":"string","title":"Borough","description":"Manhattan, Bronx, Brooklyn, Queens, Staten Island."},"bbl":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Bbl","description":"Borough-block-lot: the TAX LOT, which can hold many buildings. Never use it to identify one."},"bin":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Bin","description":"Building Identification Number: one BIN is one building. This is the identifier to join on."},"indexed":{"type":"boolean","title":"Indexed","description":"Whether a card exists. False means the address is real and we have not built it yet: nothing is known about it here, which is not the same as nothing being wrong, and `building_overview` will 404."},"lat":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Lat","description":"Latitude, WGS84."},"lng":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Lng","description":"Longitude, WGS84."}},"type":"object","required":["slug","label","address","borough","bbl","bin","indexed","lat","lng"],"title":"BuildingMatch"},"Card":{"properties":{"card_version":{"type":"string","title":"Card Version","description":"Schema version of this card document."},"generated_at":{"type":"string","title":"Generated At","description":"When this card was built, ISO timestamp."},"building_id":{"type":"string","title":"Building Id","description":"Internal id, `nyc-<BIN>`."},"identity":{"$ref":"#/components/schemas/Identity","description":"Which building this is."},"headline":{"anyOf":[{"$ref":"#/components/schemas/Headline"},{"type":"null"}],"description":"The one sentence the card leads with. Null when no rule matched."},"build":{"$ref":"#/components/schemas/BuildStats","description":"How the build went: which sections had a finding, and how long it took. Not a rating of the building."},"summary":{"$ref":"#/components/schemas/Summary"},"basics":{"$ref":"#/components/schemas/Basics","description":"Year built, stories and units, each with its source."},"systems":{"items":{"$ref":"#/components/schemas/SystemDef"},"type":"array","title":"Systems","description":"The systems the card groups facts under. Their statuses are at /v1/buildings/{slug}/systems."},"sections":{"additionalProperties":{"items":{"$ref":"#/components/schemas/FactRow"},"type":"array"},"type":"object","title":"Sections","description":"Every fact, grouped by the page section it appears in."},"records":{"additionalProperties":{"additionalProperties":{"additionalProperties":true,"type":"object"},"type":"object"},"type":"object","title":"Records","description":"The agency records kept with the card, as {kind: {record_id: {column: value}}}, allow-listed. /records serves these typed, with each type's columns named; prefer it."},"alerts":{"items":{"$ref":"#/components/schemas/Finding"},"type":"array","title":"Alerts","description":"Findings worth knowing, each naming its facts."},"notables":{"items":{"$ref":"#/components/schemas/Finding"},"type":"array","title":"Notables","description":"Findings worth surfacing that are not alerts."},"checks":{"items":{"$ref":"#/components/schemas/Check"},"type":"array","title":"Checks","description":"Reassurances: what was checked and found clean."},"owner":{"items":{"$ref":"#/components/schemas/OwnerEntry"},"type":"array","title":"Owner","description":"The registered owner and agent companies, from HPD. Individual people are never named. Empty where no registration was found."},"linked_not_owned":{"additionalProperties":{"type":"string"},"type":"object","title":"Linked Not Owned","description":"Where else to look, by name: outside sites and agency tools for this address, as links. Not ours, and not vouched for."},"area_facts":{"items":{"$ref":"#/components/schemas/AreaFact"},"type":"array","title":"Area Facts","description":"Facts about the surrounding area, never about this address."},"era_education":{"$ref":"#/components/schemas/EraEducation","description":"What a building of this age usually has, as context."},"sources":{"items":{"$ref":"#/components/schemas/CardSource"},"type":"array","title":"Sources","description":"Every dataset this card drew on."},"withheld":{"items":{"$ref":"#/components/schemas/Withheld"},"type":"array","title":"Withheld","description":"Record kinds we have not re-checked within their window and so leave out rather than serve out of date. Empty when nothing is withheld; otherwise the records here are incomplete and an absence is not 'nothing on record'."}},"type":"object","required":["card_version","generated_at","building_id","identity","headline","build","summary","basics","systems","sections","records","alerts","notables","checks","owner","linked_not_owned","area_facts","era_education","sources"],"title":"Card","description":"One building's whole card: every part typed, every known field described.\n\nA fact's `value` varies by its `kind`, so `FactRow.value` stays open, and an agency\nrecord's columns vary by record type, so `records` is a map; /records lists the\ncolumns for each type. Every part allows fields not listed here, so a column an\nagency adds later is passed through rather than deleted. For most questions the\nnarrower endpoints -- /systems, /records, /units -- are smaller and say more."},"CardSource":{"properties":{"key":{"type":"string","title":"Key","description":"The dataset key; resolve at /v1/sources."},"name":{"type":"string","title":"Name","description":"Its published title."},"agency":{"type":"string","title":"Agency","description":"Who publishes it."},"url":{"type":"string","title":"Url","description":"Where the agency publishes it."},"as_of":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"As Of","description":"When the agency last updated it."}},"additionalProperties":true,"type":"object","required":["key","name","agency","url","as_of"],"title":"CardSource"},"Check":{"properties":{"kind":{"type":"string","title":"Kind","description":"The fact kind checked; `_stale` on the withheld line."},"short":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Short","description":"A few words, for a list."},"text":{"type":"string","title":"Text","description":"The full sentence."},"source_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Name","description":"The dataset it was checked in."},"as_of":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"As Of","description":"When the agency last updated it."},"kinds":{"items":{"type":"string"},"type":"array","title":"Kinds","description":"The fact kinds it rests on."},"stale":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Stale","description":"True on the withheld line."}},"additionalProperties":true,"type":"object","required":["kind","text"],"title":"Check","description":"A reassurance: something checked in city records and found clean. On a card past\nits check-again date, withheld ones are replaced by one line saying how many\n(`stale` true), which carries only `kind`, `text` and `kinds`."},"Column":{"properties":{"name":{"type":"string","title":"Name","description":"The field name as it appears in `fields`/`items`.","examples":["originalcertifybydate"]},"label":{"type":"string","title":"Label","description":"What that field means, in a reader's words. The agency's column names are not self-explanatory.","examples":["Certify by"]}},"type":"object","required":["name","label"],"title":"Column"},"Complex":{"properties":{"name":{"type":"string","title":"Name","description":"The development's name, as HPD registers it."},"source":{"type":"string","title":"Source","description":"The dataset key it came from."}},"additionalProperties":true,"type":"object","required":["name","source"],"title":"Complex"},"Conflict":{"properties":{"value":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Value","description":"What the other source says."},"source":{"type":"string","title":"Source","description":"The other source's dataset key."},"scope":{"type":"string","title":"Scope","description":"`building` or `lot`."},"note":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Note","description":"Why they disagree, where known."},"source_name":{"type":"string","title":"Source Name","description":"That dataset's published title."}},"additionalProperties":true,"type":"object","required":["value","source","scope","note","source_name"],"title":"Conflict"},"Coverage":{"properties":{"indexed_total":{"type":"integer","title":"Indexed Total","description":"How many buildings have a card. Coverage grows a neighbourhood at a time; an un-indexed building returns 404 rather than a guess."},"by_borough":{"additionalProperties":{"type":"integer"},"type":"object","title":"By Borough","description":"The same total split by borough.","examples":[{"Manhattan":18}]},"slugs":{"items":{"type":"string"},"type":"array","title":"Slugs","description":"Indexed slugs for this page, usable directly at /v1/buildings/{slug}. Walk with ?offset=&limit=."},"returned":{"type":"integer","title":"Returned","description":"How many slugs this page contains."},"offset":{"type":"integer","title":"Offset","description":"Where this page started."},"has_more":{"type":"boolean","title":"Has More","description":"Whether more indexed buildings follow. This list used to be capped silently, which made a partial answer look complete."}},"type":"object","required":["indexed_total","by_borough","slugs","returned","offset","has_more"],"title":"Coverage"},"EraEducation":{"properties":{"year":{"type":"integer","title":"Year","description":"The year built it is keyed to."},"text":{"items":{"type":"string"},"type":"array","title":"Text","description":"Sentences about buildings of that era."},"questions":{"items":{"type":"string"},"type":"array","title":"Questions","description":"Questions worth asking a landlord or seller."},"disclaimer":{"type":"string","title":"Disclaimer","description":"What this is not."}},"additionalProperties":true,"type":"object","required":["year","text","questions","disclaimer"],"title":"EraEducation","description":"What a building of this age usually has: context, not a claim about this one."},"EventIn":{"properties":{"event":{"type":"string","title":"Event","description":"One of the allowed event names; anything else is refused. See blueflo/web/telemetry.py::EVENTS.","examples":["share"]},"slug":{"type":"string","maxLength":120,"title":"Slug","description":"Which building the event is about, if any. Recorded in the log, never as a metric label.","default":""}},"type":"object","required":["event"],"title":"EventIn","description":"What a page may report about itself. Deliberately tiny."},"FactRow":{"properties":{"kind":{"type":"string","title":"Kind","description":"What this fact is, in a controlled vocabulary.","examples":["heat_source"]},"label":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Label","description":"Its name for a reader."},"display":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Display","description":"The fact as a sentence, ready to show. This is the field to quote."},"value":{"title":"Value","description":"The underlying value, whose type depends on `kind`: a number, a string, or an object carrying `items`/`timeline` for a fact that is a list of records. Null where only `display` is meaningful."},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"`found`, `no_record`, `not_required` or `stale`. `no_record` means the city has nothing, which is not the same as nothing being wrong. `stale` means we have not re-checked this fact inside its window, so `display` says so and `value` is null -- treat it as unverified, never as false.","examples":["no_record"]},"section":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Section","description":"Which part of the page this belongs to."},"scope":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Scope","description":"What the fact is ABOUT: `building`, `lot` (shared with other buildings) or `area` (a census tract). An area fact is never address-level.","examples":["building"]},"source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source","description":"The dataset key; `source_name` says it in words."},"source_name":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source Name","description":"That dataset's published title."},"record_date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Record Date","description":"When the underlying record is dated, in the agency's own format. Null where the fact has no single date."},"as_of":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"As Of","description":"When the agency last updated the dataset this fact comes from, ISO date. Not when we looked: see `checked_at` and `stale_after`."},"checked_at":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Checked At","description":"The last date we confirmed this fact still stands, set when a nightly check found its source unchanged for this building. Absent on a fact last confirmed when its card was built."},"stale_after":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Stale After","description":"The date this fact stops being asserted. Past that, treat it as unverified rather than false."},"definition":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Definition","description":"What the number counts, where that is not obvious — written because a count with no definition gets misread."}},"type":"object","required":["kind","label","display","value","status","section","scope","source","source_name","record_date","as_of","stale_after","definition"],"title":"FactRow"},"Finding":{"properties":{"text":{"type":"string","title":"Text","description":"The sentence."},"kinds":{"items":{"type":"string"},"type":"array","title":"Kinds","description":"The fact kinds it rests on."},"kind":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Kind","description":"`_stale` on the line saying how many findings were withheld."},"stale":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Stale","description":"True on that line."}},"additionalProperties":true,"type":"object","required":["text"],"title":"Finding","description":"An alert or a notable: a sentence and the facts it rests on."},"HTTPValidationError":{"properties":{"detail":{"items":{"$ref":"#/components/schemas/ValidationError"},"type":"array","title":"Detail"}},"type":"object","title":"HTTPValidationError"},"Headline":{"properties":{"tier":{"type":"string","title":"Tier","description":"`alert` (something worth knowing) or `reassurance` (records are clean); `stale` when withheld.","examples":["alert"]},"text":{"type":"string","title":"Text","description":"The sentence, from a reviewed template."},"kinds":{"items":{"type":"string"},"type":"array","title":"Kinds","description":"The fact kinds it rests on."},"sources":{"items":{"type":"string"},"type":"array","title":"Sources","description":"The datasets those came from."},"as_of":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"As Of","description":"The newest as-of date behind it."},"stale":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Stale","description":"True when withheld as not re-checked."}},"additionalProperties":true,"type":"object","required":["tier","text"],"title":"Headline","description":"The one sentence a card leads with."},"Health":{"properties":{"ok":{"type":"boolean","title":"Ok","description":"True when the service is up and can read its cards."},"cached_cards":{"type":"integer","title":"Cached Cards","description":"How many building cards the index lists."},"last_checked":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Last Checked","description":"When the nightly job last checked any source, ISO 8601 UTC. None if it never has."},"hours_since_check":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Hours Since Check","description":"Hours since `last_checked`. Past the configured limit the response is 503: the nightly job has stopped."},"reason":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Reason","description":"Why `ok` is false, when it is."}},"type":"object","required":["ok","cached_cards"],"title":"Health"},"Identity":{"properties":{"input":{"type":"string","title":"Input","description":"The address as it was looked up."},"primary_address":{"type":"string","title":"Primary Address","description":"The address of record this card is named after."},"geocoder_label":{"type":"string","title":"Geocoder Label","description":"The full label the city's geocoder returned."},"borough":{"type":"string","title":"Borough","description":"Manhattan, Bronx, Brooklyn, Queens, Staten Island."},"jurisdiction":{"type":"string","title":"Jurisdiction","description":"Which city's records apply. Always NYC today."},"bin":{"type":"string","title":"Bin","description":"Building Identification Number: one building."},"bbl":{"type":"string","title":"Bbl","description":"Borough-block-lot: the tax lot, which can hold several buildings."},"lat":{"type":"number","title":"Lat","description":"Latitude, WGS84."},"lng":{"type":"number","title":"Lng","description":"Longitude, WGS84."},"zip":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Zip","description":"ZIP code."},"hpd_building_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Hpd Building Id","description":"HPD's own id for the building, where it registers one."},"all_addresses":{"items":{"type":"string"},"type":"array","title":"All Addresses","description":"Every address on this building. Each one opens this card."},"other_boroughs_with_same_address":{"items":{"type":"string"},"type":"array","title":"Other Boroughs With Same Address","description":"Boroughs where the same street address names a different building."},"lot_shared_with_other_buildings":{"type":"boolean","title":"Lot Shared With Other Buildings","description":"Whether other buildings stand on the same tax lot, so a lot-level fact is not only about this one."},"buildings_on_lot":{"type":"integer","title":"Buildings On Lot","description":"How many buildings stand on the tax lot."},"address_slug":{"type":"string","title":"Address Slug","description":"The address alone as a slug, before any disambiguation between buildings."},"buildings_at_address":{"type":"integer","title":"Buildings At Address","description":"How many buildings answer to this address."},"complex":{"anyOf":[{"$ref":"#/components/schemas/Complex"},{"type":"null"}],"description":"The development this building belongs to, if any."}},"additionalProperties":true,"type":"object","required":["input","primary_address","geocoder_label","borough","jurisdiction","bin","bbl","lat","lng","zip","hpd_building_id","all_addresses","other_boroughs_with_same_address","lot_shared_with_other_buildings","buildings_on_lot","address_slug","buildings_at_address","complex"],"title":"Identity","description":"Which building a card is about."},"IndexMatch":{"properties":{"slug":{"type":"string","title":"Slug","description":"The building's id here."},"address":{"type":"string","title":"Address","description":"The address of record."},"borough":{"type":"string","title":"Borough","description":"The borough."},"zip":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Zip","description":"ZIP code, from PLUTO."},"bin":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Bin","description":"Building Identification Number."},"bbl":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Bbl","description":"Borough-block-lot (the tax lot)."},"lat":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Lat","description":"Latitude, WGS84."},"lng":{"anyOf":[{"type":"number"},{"type":"null"}],"title":"Lng","description":"Longitude, WGS84."},"headline":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Headline","description":"The one sentence this card leads with, composed from reviewed templates rather than generated per building."},"tier":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Tier","description":"How the headline reads: `alert` (something needs attention), `reassurance` (records are clean), or `neutral`.","examples":["alert"]},"year_built":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Year Built","description":"Year built, from PLUTO."},"units":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Units","description":"Residential units, from PLUTO."},"owners":{"items":{"type":"string"},"type":"array","title":"Owners","description":"Owning COMPANIES as registered with HPD. Individual people are never named."},"systems":{"additionalProperties":{"type":"string"},"type":"object","title":"Systems","description":"Each system's status as a sentence, keyed by system. Same wording the building page shows."},"aliases":{"items":{"type":"string"},"type":"array","title":"Aliases","description":"The building's other addresses here, as slugs. One building often has several doors; each of these redirects to this card. Empty for a building with one address."}},"type":"object","required":["slug","address","borough","zip","bin","bbl","lat","lng","headline","tier","year_built","units","owners","systems"],"title":"IndexMatch"},"IndexResults":{"properties":{"searched":{"type":"integer","title":"Searched","description":"How many indexed buildings were considered."},"matched":{"type":"integer","title":"Matched","description":"How many met every filter."},"note":{"type":"string","title":"Note","description":"What was and was not searched."},"results":{"items":{"$ref":"#/components/schemas/IndexMatch"},"type":"array","title":"Results","description":"The matching buildings."}},"type":"object","required":["searched","matched","note","results"],"title":"IndexResults"},"OwnerEntry":{"properties":{"name":{"type":"string","title":"Name","description":"The company's name. An individual appears as 'Individual owner', never by name."},"role":{"type":"string","title":"Role","description":"`CorporateOwner`, `TaxLotOwner`, `Agent` or `IndividualOwner`, as HPD records it."},"source":{"type":"string","title":"Source","description":"The dataset key."},"source_name":{"type":"string","title":"Source Name","description":"That dataset's published title."}},"additionalProperties":true,"type":"object","required":["name","role","source","source_name"],"title":"OwnerEntry","description":"One registered party, from HPD's registration contacts."},"PeerComparison":{"properties":{"topic":{"type":"string","title":"Topic","description":"The problem compared, in the card's vocabulary.","examples":["heat or hot water"]},"sentence":{"type":"string","title":"Sentence","description":"How this building compares with similar-size buildings in its own community district, ready to quote. Quote it as written: the wording is the claim the data supports, and a percentile is not.","examples":["More reports than 9 in 10 similar-size buildings in Washington Heights & Inwood"]},"basis":{"type":"string","title":"Basis","description":"What the comparison counted, as a sentence: which reports, over what window, against how many buildings of what size. Say it alongside `sentence` when a reader may compare it with the complaint count."},"reports":{"type":"integer","title":"Reports","description":"This building's reports of the problem as the page's grid counts them: complaints within 7 days of the first are one report, over the whole years the card holds. So it is smaller than the complaint count in `status`, which counts every complaint."},"peers":{"type":"integer","title":"Peers","description":"How many similar-size buildings it was compared with."}},"type":"object","required":["topic","sentence","basis","reports","peers"],"title":"PeerComparison"},"PermitInJob":{"properties":{"trade":{"type":"string","title":"Trade","description":"The work this permit covers, ALWAYS a two- or three-letter code. Legacy BIS publishes one and DOB NOW publishes plain English for the same trades, so both are normalised to one vocabulary here — group on this. `AN`, `ST` and `EL` are ours rather than DOB's, for trades BIS filed under the parent job. The agency's own spelling is still in `fields.work_type`.","examples":["PL"]},"trade_label":{"type":"string","title":"Trade Label","description":"That code in words, as the page shows it. Two permits can share a code and differ here when the agency drew a distinction the code does not — supported and suspended scaffold are both `SF`. Differences of capitalisation alone are collapsed.","examples":["Plumbing"]},"sequence_no":{"type":"string","title":"Sequence No","description":"DOB's sequence number within the job. Context, not an id: the city reuses it, so two permits of one job and trade can both be numbered 2."},"issued":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Issued","description":"When this permit was issued, ISO date. Normalised here even though `fields` keeps the agency's own spelling: the city publishes two formats and one job's permits arrived in both."},"expires":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Expires","description":"When it expired or will, ISO date."},"filing":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Filing","description":"Why it was filed — INITIAL or RENEWAL."},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"The agency's status for this permit."}},"type":"object","required":["trade","trade_label","sequence_no","issued","expires","filing","status"],"title":"PermitInJob","description":"One permit of a DOB job.\n\nA job holds a permit per TRADE and renews each by issuing another, so three\npermits numbered 01 on one job are plumbing, mechanical and general construction\nrather than a sequence. The number is not an identifier either: DOB reuses it\nwithin a job and trade. Read these in date order, which is how they are returned."},"RecordBlock":{"properties":{"kind":{"type":"string","title":"Kind","description":"The record type: `complaint_patterns`, `dob_violations`, `hpd_violations`, `permits`.","examples":["hpd_violations"]},"count":{"type":"integer","title":"Count","description":"How many records of this kind EXIST on this card — not how many this page returned. Use it with `offset` and `has_more` to walk."},"returned":{"type":"integer","title":"Returned","description":"How many records this page contains."},"offset":{"type":"integer","title":"Offset","description":"Where this page started."},"has_more":{"type":"boolean","title":"Has More","description":"Whether another page follows. Walk with ?offset=&limit=; the order is stable across requests."},"columns":{"items":{"$ref":"#/components/schemas/Column"},"type":"array","title":"Columns","description":"The shape of every record below, in display order. This is the allow-list: a column the agency adds cannot appear here or in `items` until it is added deliberately."},"items":{"additionalProperties":{"additionalProperties":true,"type":"object"},"type":"object","title":"Items","description":"The records, keyed by the agency's own id for each. Inner values are strings as the agency publishes them — dates included, which is why `columns` carries labels rather than types. Each also carries `page` (its page on this site, absolute), `record` (the agency's permalink, or null) and, for a permit, `sequence` — every permit on that DOB job, so a renewal is visible from the list rather than only after fetching the record."}},"type":"object","required":["kind","count","returned","offset","has_more","columns","items"],"title":"RecordBlock"},"RecordDetail":{"properties":{"slug":{"type":"string","title":"Slug","description":"The building's id here."},"kind":{"type":"string","title":"Kind","description":"The record type."},"record_id":{"type":"string","title":"Record Id","description":"The agency's own id. May contain a slash — DOB violation V101116UB1004/16 does — so it is the final, variable-length part of the path and `dataset` is a query parameter."},"dataset":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Dataset","description":"Which dataset this record came from, where one kind spans several: `bis`, `ecb` or `safety` for a DOB violation, `bis_permits` or `dobnow_permits` for a permit. Null where the kind has one dataset."},"columns":{"items":{"$ref":"#/components/schemas/Column"},"type":"array","title":"Columns","description":"The shape and labels for this kind, in display order."},"fields":{"additionalProperties":true,"type":"object","title":"Fields","description":"This record's values, keyed by column name, allow-listed. Strings as the agency publishes them."},"sequence":{"items":{"$ref":"#/components/schemas/PermitInJob"},"type":"array","title":"Sequence","description":"For a permit: every permit on this DOB job, oldest first. A job is renewed by issuing another permit and carries one per trade, so this is the whole job rather than the single row the id resolves to. Empty for every other record kind."},"page":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Page","description":"The human-readable page for this record on this site."},"source":{"$ref":"#/components/schemas/RecordSourceRef","description":"Where the agency publishes it."},"as_of":{"type":"string","title":"As Of","description":"When we last checked this dataset, ISO date."},"contains":{"type":"string","title":"Contains","description":"What kind of data this endpoint returns."},"excludes":{"type":"string","title":"Excludes","description":"What it deliberately never returns."},"terms":{"type":"string","title":"Terms","description":"The one use that is prohibited."}},"type":"object","required":["slug","kind","record_id","dataset","columns","fields","page","source","as_of","contains","excludes","terms"],"title":"RecordDetail"},"RecordSlice":{"properties":{"slug":{"type":"string","title":"Slug","description":"The building's id here."},"records":{"items":{"$ref":"#/components/schemas/RecordBlock"},"type":"array","title":"Records","description":"One block per record kind. Narrow with ?kind=."},"contains":{"type":"string","title":"Contains","description":"What kind of data this endpoint returns."},"excludes":{"type":"string","title":"Excludes","description":"What it deliberately never returns."},"terms":{"type":"string","title":"Terms","description":"The one use that is prohibited."},"withheld":{"items":{"$ref":"#/components/schemas/Withheld"},"type":"array","title":"Withheld","description":"Record kinds we have not re-checked within their window and so leave out rather than serve out of date. Empty when nothing is withheld; otherwise the records here are incomplete and an absence is not 'nothing on record'."}},"type":"object","required":["slug","records","contains","excludes","terms"],"title":"RecordSlice"},"RecordSourceRef":{"properties":{"name":{"type":"string","title":"Name","description":"The publishing dataset's title."},"dataset_url":{"type":"string","title":"Dataset Url","description":"That whole dataset on NYC Open Data."},"record_url":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Record Url","description":"A permalink to THIS record on NYC Open Data, or null when the record carries no id we can address. Never a guess: a link to the wrong record is worse than no link."}},"type":"object","required":["name","dataset_url","record_url"],"title":"RecordSourceRef"},"SearchResults":{"properties":{"query":{"type":"string","title":"Query","description":"The query as received."},"results":{"items":{"$ref":"#/components/schemas/BuildingMatch"},"type":"array","title":"Results","description":"Matches, best first. More than one borough can match the same house number and street; the caller picks and we never guess."},"note":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Note","description":"Why more than one result can be correct, when more than one borough matched; else null."}},"type":"object","required":["query","results","note"],"title":"SearchResults"},"Source":{"properties":{"key":{"type":"string","title":"Key","description":"Internal id for this dataset. Every fact on a card names one of these in its `source` field.","examples":["hpd_viol"]},"name":{"type":"string","title":"Name","description":"The dataset's published title.","examples":["Housing Maintenance Code Violations"]},"agency":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Agency","description":"The NYC agency that publishes it.","examples":["HPD"]},"dataset_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Dataset Id","description":"NYC Open Data's four-four id. The dataset lives at https://data.cityofnewyork.us/d/<dataset_id>.","examples":["wvxf-dwi5"]}},"type":"object","required":["key","name","agency","dataset_id"],"title":"Source"},"SourceList":{"properties":{"sources":{"items":{"$ref":"#/components/schemas/Source"},"type":"array","title":"Sources","description":"Every dataset any card can draw on, sorted by key."}},"type":"object","required":["sources"],"title":"SourceList"},"Summary":{"properties":{"headline":{"anyOf":[{"$ref":"#/components/schemas/Headline"},{"type":"null"}],"description":"The headline again."},"tiles":{"items":{"$ref":"#/components/schemas/Tile"},"type":"array","title":"Tiles","description":"Up to four status tiles."},"checks":{"items":{"$ref":"#/components/schemas/Check"},"type":"array","title":"Checks","description":"Up to three reassurances."},"more_flags":{"items":{"type":"string"},"type":"array","title":"More Flags","description":"Further findings, one sentence each."},"detail_sections":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Detail Sections","description":"How many sections the full card has."},"stale":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Stale","description":"True when withheld as not re-checked."}},"additionalProperties":true,"type":"object","title":"Summary","description":"What a link preview and the card image show."},"SystemDef":{"properties":{"key":{"type":"string","title":"Key","description":"System id, as /v1/buildings/{slug}/systems/{key} takes it.","examples":["heat"]},"label":{"type":"string","title":"Label","description":"Its name for a reader."},"kinds":{"items":{"type":"string"},"type":"array","title":"Kinds","description":"The fact kinds that feed it."},"record":{"type":"string","title":"Record","description":"The record kind its detail comes from."}},"additionalProperties":true,"type":"object","required":["key","label","kinds","record"],"title":"SystemDef","description":"One system a card groups its facts under."},"SystemDetail":{"properties":{"slug":{"type":"string","title":"Slug","description":"The building's id here."},"system":{"type":"string","title":"System","description":"The system key that was asked for."},"label":{"type":"string","title":"Label","description":"Its name for a reader."},"page":{"type":"string","title":"Page","description":"The page a person reads this on, as an absolute URL. Link it when quoting."},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"The answer as a sentence, or null where this system has no at-a-glance answer. See SystemSummary.status."},"question":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Question","description":"The question this system answers."},"comparison":{"anyOf":[{"items":{"$ref":"#/components/schemas/PeerComparison"},"type":"array"},{"type":"null"}],"title":"Comparison","description":"Peer comparison for this system's complaint topics, one per topic with enough reports. **Null is not 'typical'**: `comparison_note` says why nothing was compared."},"comparison_note":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Comparison Note","description":"Why `comparison` is null, as a sentence; null when it is not."},"records":{"items":{"$ref":"#/components/schemas/FactRow"},"type":"array","title":"Records","description":"Every fact behind that sentence, each with its own source and date."},"events":{"items":{"$ref":"#/components/schemas/TopicEvent"},"type":"array","title":"Events","description":"The violations, complaints and permits about this system, newest first: the evidence behind the status."},"events_total":{"type":"integer","title":"Events Total","description":"How many there are in all."},"events_note":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Events Note","description":"Where to read the rest when `events` is not all of them; else null."}},"type":"object","required":["slug","system","label","page","status","question","comparison","comparison_note","records","events","events_total","events_note"],"title":"SystemDetail"},"SystemList":{"properties":{"slug":{"type":"string","title":"Slug","description":"The building's id here."},"address":{"type":"string","title":"Address","description":"The address of record."},"page":{"type":"string","title":"Page","description":"The page a person reads this on, as an absolute URL. Link it when quoting."},"as_of":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"As Of","description":"When this card was built from city records."},"headline":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Headline","description":"The one thing most worth knowing, as a sentence, or null where nothing stands out."},"comparison_note":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Comparison Note","description":"Why nothing in this building was compared with similar buildings, when the reason is the building's; each system then points here. Null when systems may be compared."},"systems":{"items":{"$ref":"#/components/schemas/SystemSummary"},"type":"array","title":"Systems","description":"Every system, in the order the building page shows them. An agent asked 'is this building okay?' wants these lines, not the whole card."},"record_counts":{"additionalProperties":{"type":"integer"},"type":"object","title":"Record Counts","description":"How many records of each kind this building has; read them with `records`."},"apartments":{"$ref":"#/components/schemas/Apartments","description":"Apartments named in city records."},"withheld":{"items":{"$ref":"#/components/schemas/Withheld"},"type":"array","title":"Withheld","description":"Record kinds we have not re-checked within their window and so leave out rather than serve out of date. Empty when nothing is withheld; otherwise the records here are incomplete and an absence is not 'nothing on record'."}},"type":"object","required":["slug","address","page","as_of","headline","comparison_note","systems","record_counts","apartments"],"title":"SystemList"},"SystemSummary":{"properties":{"key":{"type":"string","title":"Key","description":"System id; pass it to `building_topic`.","examples":["heat"]},"label":{"type":"string","title":"Label","description":"Its name for a reader.","examples":["Heat and hot water"]},"question":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Question","description":"The question this system answers, phrased as a resident would ask it.","examples":["Will I have heat?"]},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status","description":"The answer as a sentence, ready to show. Never a code. **Null where this system has no at-a-glance answer** -- gas, because the city publishes no inspection results for any building, and energy, because benchmarking only covers buildings over 25,000 sq ft. Null is not 'no issues': `building_topic` carries what the agencies do say.","examples":["No issues on record"]},"tone":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Tone","description":"How to colour that sentence: `ok`, `old` (only older records), `na` (does not apply to this building), `warn`, `alert`. Null with a null `status`.","examples":["ok"]},"detail":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Detail","description":"A second sentence where one is warranted, else null."},"comparison":{"anyOf":[{"items":{"$ref":"#/components/schemas/PeerComparison"},"type":"array"},{"type":"null"}],"title":"Comparison","description":"Peer comparison for this system's complaint topics, one per topic with enough reports. **Null is not 'typical'**: `comparison_note` says why nothing was compared."},"comparison_note":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Comparison Note","description":"Why `comparison` is null, as a sentence; null when it is not."}},"type":"object","required":["key","label","question","status","tone","detail","comparison","comparison_note"],"title":"SystemSummary"},"Tile":{"properties":{"label":{"type":"string","title":"Label","description":"What the tile is about."},"value":{"type":"string","title":"Value","description":"Its status, in words."},"note":{"type":"string","title":"Note","description":"One line of detail."},"source_name":{"type":"string","title":"Source Name","description":"Where it came from."},"as_of":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"As Of","description":"When the agency last updated it."}},"additionalProperties":true,"type":"object","required":["label","value","note","source_name","as_of"],"title":"Tile"},"TopicEvent":{"properties":{"date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Date","description":"When it was filed or inspected."},"record":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Record","description":"What it is, in words: HPD violation, DOB violation, complaint or permit."},"kind":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Kind","description":"Its record kind, as `record` takes it."},"about":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"About","description":"What it is about, in the card's vocabulary."},"tags":{"items":{"type":"string"},"type":"array","title":"Tags","description":"Qualifiers such as a violation's class."},"open":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Open","description":"Whether it is still open, where that applies."},"severe":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Severe","description":"Whether the city rates it most serious."},"unit":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Unit","description":"The apartment it names, if any."},"record_id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Record Id","description":"The agency's id; pass it to `record`."},"dataset":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Dataset","description":"Which dataset, where a kind spans several."},"page":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Page","description":"The page a person reads this on, as an absolute URL. Link it when quoting."}},"type":"object","required":["date","record","kind","about","tags","open","severe","unit","record_id","dataset","page"],"title":"TopicEvent"},"UnitDetail":{"properties":{"slug":{"type":"string","title":"Slug","description":"The building's id here."},"unit":{"type":"string","title":"Unit","description":"The apartment, in the spelling the CITY used. Ask for '4-r' and this comes back '4R', because that is the label the records carry."},"requested":{"type":"string","title":"Requested","description":"The label as asked for, before resolution."},"known":{"type":"boolean","title":"Known","description":"Whether any public record names this apartment. False is a true answer and not an error: most apartments are named in none. The endpoint returns 200 with an empty list rather than 404, because 404 would mean 'no such apartment' when what is meant is 'nothing was ever filed about it'."},"count":{"type":"integer","title":"Count","description":"How many records name it. Agrees with /units."},"records":{"items":{"$ref":"#/components/schemas/UnitRecord"},"type":"array","title":"Records","description":"Those records, newest first."},"page":{"type":"string","title":"Page","description":"The page for this apartment, as an absolute URL."},"building_wide":{"items":{"additionalProperties":{"anyOf":[{"type":"string"},{"type":"null"}]},"type":"object"},"type":"array","title":"Building Wide","description":"Systems with issues on record for the whole building, each as `key`, `label` and `status`. They apply to this apartment too: an apartment named in no record is not one with nothing wrong."},"note":{"type":"string","title":"Note","description":"What this list is, and what its absence means."},"contains":{"type":"string","title":"Contains","description":"What kind of data this endpoint returns."},"excludes":{"type":"string","title":"Excludes","description":"What it deliberately never returns."},"terms":{"type":"string","title":"Terms","description":"The one use that is prohibited."},"withheld":{"items":{"$ref":"#/components/schemas/Withheld"},"type":"array","title":"Withheld","description":"Record kinds we have not re-checked within their window and so leave out rather than serve out of date. Empty when nothing is withheld; otherwise the records here are incomplete and an absence is not 'nothing on record'."}},"type":"object","required":["slug","unit","requested","known","count","records","page","building_wide","note","contains","excludes","terms"],"title":"UnitDetail"},"UnitList":{"properties":{"slug":{"type":"string","title":"Slug","description":"The building's id here."},"units":{"items":{"$ref":"#/components/schemas/UnitRef"},"type":"array","title":"Units","description":"Apartments named in a public record. Most apartments are named in none, which is the usual case and not a gap."},"apartments_in_building":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Apartments In Building","description":"Total residential units from PLUTO, for scale: '3 apartments' means something different in a 4-unit walk-up and a 500-unit tower."},"coverage":{"type":"string","title":"Coverage","description":"That comparison as a sentence."},"note":{"type":"string","title":"Note","description":"What this list is and is not."},"contains":{"type":"string","title":"Contains","description":"What kind of data this endpoint returns.","examples":["city records only"]},"excludes":{"type":"string","title":"Excludes","description":"What it deliberately never returns."},"terms":{"type":"string","title":"Terms","description":"The one use that is prohibited.","examples":["May not be used to screen or refuse a tenant."]},"withheld":{"items":{"$ref":"#/components/schemas/Withheld"},"type":"array","title":"Withheld","description":"Record kinds we have not re-checked within their window and so leave out rather than serve out of date. Empty when nothing is withheld; otherwise the records here are incomplete and an absence is not 'nothing on record'."}},"type":"object","required":["slug","units","apartments_in_building","coverage","note","contains","excludes","terms"],"title":"UnitList"},"UnitRecord":{"properties":{"kind":{"type":"string","title":"Kind","description":"The record type, same vocabulary as /records."},"topic":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Topic","description":"What the record is about, from a controlled vocabulary — 'heat or hot water', 'pests'. Never the agency's free text."},"date":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Date","description":"When the record is dated."},"class":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Class","description":"HPD violation class: A (non-hazardous), B (hazardous) or C (immediately hazardous)."},"severity":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Severity","description":"Severity where the agency states one."},"paperwork":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Paperwork","description":"True where the violation is a filing failure rather than a physical condition — a missing registration is not a leak."},"closed":{"anyOf":[{"type":"boolean"},{"type":"null"}],"title":"Closed","description":"Whether the agency has closed it."},"id":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Id","description":"The agency's id for this record."},"dataset":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Dataset","description":"Which dataset it came from."},"source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source","description":"The dataset key, such as `hpd_viol`."},"page":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Page","description":"This record's page on this site, as an absolute URL, where addressable."},"record":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Record","description":"This record's permalink on NYC Open Data, or null."}},"type":"object","required":["kind","topic","date"],"title":"UnitRecord","description":"One city record that names this apartment.\n\nThe fields are `render/unit_page.PUBLIC_FIELDS` and nothing else. That list is\nshorter than what a building surface may say, deliberately: an HPD violation\nexists because somebody in that apartment complained, and its free text names\nthem in most cases. The topic from a controlled vocabulary is published; the\norder text is not."},"UnitRef":{"properties":{"label":{"type":"string","title":"Label","description":"The apartment as the city wrote it.","examples":["4B"]},"slug":{"type":"string","title":"Slug","description":"URL-safe form of that label."},"records":{"type":"integer","title":"Records","description":"How many public records name this apartment."},"path":{"type":"string","title":"Path","description":"The human-readable page for it on this site."}},"type":"object","required":["label","slug","records","path"],"title":"UnitRef"},"ValidationError":{"properties":{"loc":{"items":{"anyOf":[{"type":"string"},{"type":"integer"}]},"type":"array","title":"Location"},"msg":{"type":"string","title":"Message"},"type":{"type":"string","title":"Error Type"},"input":{"title":"Input"},"ctx":{"type":"object","title":"Context"}},"type":"object","required":["loc","msg","type"],"title":"ValidationError"},"Withheld":{"properties":{"kind":{"type":"string","title":"Kind","description":"The record kind, as in /records: hpd_violations, …"},"label":{"type":"string","title":"Label","description":"What it is called on the page."},"source":{"type":"string","title":"Source","description":"The dataset it comes from."},"checked":{"type":"string","title":"Checked","description":"The last date we checked it, YYYY-MM-DD."}},"type":"object","required":["kind","label","source","checked"],"title":"Withheld","description":"One kind of record we have not re-checked within its window, and so do not serve.\nIts records are left out rather than shown out of date: a violation stored a week ago\nmay have closed since."}}}}