CA Food Facility Inspections - San Francisco Restaurant History avatar

CA Food Facility Inspections - San Francisco Restaurant History

Pricing

from $0.03 / 1,000 inspection records

Go to Apify Store
CA Food Facility Inspections - San Francisco Restaurant History

CA Food Facility Inspections - San Francisco Restaurant History

SF restaurant / food-facility inspection history (public data, 2016-present, ~126k records): pass / conditional / closure, violation codes + text, scores, risk. Compliance & closure diligence for franchise / restaurant buyers.

Pricing

from $0.03 / 1,000 inspection records

Rating

0.0

(0)

Developer

Wenhao Yang

Wenhao Yang

Maintained by Community

Actor stats

1

Bookmarked

1

Total users

0

Monthly active users

5 days ago

Last modified

Categories

Share

San Francisco's Department of Public Health publishes its food-facility inspection history as open data (city Socrata, free public data). The catch: the city has published it in three successive datasets with different schemas, so a naive lookup only ever sees one slice. This actor merges all three into one queryable, charged-per-record API - the full SF restaurant inspection history from 2016 to today.

Built for: restaurant / ghost-kitchen / franchise compliance & closure diligence, supply-chain vetting, insurance, and food-safety research.

What it covers

San Francisco food-facility inspections, 2016 -> present (~126k records across three eras):

EraRowsGranularityWhat it records
current (2024-present)~22kper inspectionPass / Conditional Pass / Closure, violation codes + code text + violation count, exact permit number, DBA, neighborhood, inspector
y2020_2023~50kper violationPASS / CONDITIONAL PASS / CLOSURE, violation severity (Minor / Major / OUT...), description
y2016_2019~54kper violationinspection score (0-100), risk category (High / Moderate / Low), violation description

Why three eras? SF changed systems in 2016, 2020 and 2024 - the old tables froze and a new one started, with a ~2023-08 -> 2024-01 gap between eras. There is no exact key linking a business across all three, so cross-era history is matched on business name (generation: all). Within the current era, permit_number is the stable per-business key.

Note on era-specific filters: only the eras that actually record a field honor a filter on it. A rating / closure filter runs against the current and 2020-2023 eras only (the 2016-2019 era has no rating column - it records a score instead), so "show every closure across SF locations" returns closures from 2020 onward. Use risk / minScore for the 2016-2019 era.

Typical questions

  • "Show every Closure a restaurant chain has had across its SF locations."
  • "What violations does this food facility (by permit number) have on its latest inspections?"
  • "Which violations mention rodents / vermin / improper cooling - current and historical?"
  • "Find high-risk (or low-score) inspections from the 2016-2019 era for this business."
  • "How many Conditional Pass results did restaurants in the Mission get last year?"

Results vs. violations - row semantics

Each era has its own row granularity, and the generation field tells you which:

  • current = one row per inspection (violation text is the full violation_codes blob; violationCount = how many).
  • y2020_2023 / y2016_2019 = one row per violation (a clean inspection still emits one row with empty violation text).

Inputs

InputWhat it does
generationcurrent (default) / y2020_2023 / y2016_2019 / all (full history by name)
businessbusiness-name substring
permitexact permit number (current era only - the stable store key)
dateFrom / dateToinspection date window
ratingpass / conditional / closure
keywordviolation-text substring
riskHigh / Moderate / Low (2016-2019 era)
severityviolation severity text (2020-2023 era)
minScoreonly inspections scoring at least this (2016-2019 era)
aggregate / groupByone row per group (rating / neighborhood / inspectionType / severity / risk) with a count
maxResultscap records (default 50)

Default run = the ~50 most recent SF inspections (2024-present era) - fast enough for the daily auto-test, and a live look at what SF inspectors are finding right now.

Note: a run is capped at $5 of usage - a request large enough to reach it (roughly 5,000 records at the entry price) is cut off part-way, and the truncated run still reports success. For whole-corpus counts, use aggregate.

Example inputs

Latest inspections for one restaurant - business is a case-insensitive substring; the default current era is one row per inspection.

{"business": "Zingari", "maxResults": 5}

Trace one business across all three eras - generation=all matches on business name and returns the pre-2024 rows too.

{"business": "Zingari", "generation": "all", "maxResults": 20}

Every closure across the city - rating=closure runs against the current and 2020-2023 eras.

{"rating": "closure", "maxResults": 25}

Inspections whose violation text mentions a term - keyword matches the violation text.

{"keyword": "vermin", "maxResults": 10}

Low cost

From $0.00005 per record, down to $0.00003 at Gold - billed only for the rows you use, and each record is metered individually.

Behind this is an awkward source, unified. SF has published its food-inspection history as three successive datasets with different schemas (2016-2019 carries a 0-100 score, 2020-2023 carries a Pass/Conditional/Closure rating, 2024+ is per-inspection with violation codes) - and there is no key linking a restaurant across them; even the rating enum was once mistyped by the city (CONDITIIONAL). We normalize all three onto one schema, one rating vocabulary, and one cross-era store history matched on name - with the future-dated garbage rows SF lets into its tables clamped out so a date filter can never surface a 2031 inspection. You query one clean history; the schema archaeology stays on our side.

Example output

One inspection - business=Zingari on the default current era returns ZINGARI RISTORANTE's rows (permit is the exact per-business key); one of them:

{
"platform": "ca-food-safety",
"source": "sf-food-current",
"city": "San Francisco",
"generation": "2024-present",
"mode": "rows",
"date": "2026-09-15",
"year": "2026",
"inspectionType": "",
"rating": "Pass",
"score": "",
"severity": "",
"riskCategory": "",
"violationText": "113996, 113998, 114037, 114429, 114429.3, 114429.5 - Keep potentially hazardous foods (PHF) cold at 41F or below or hot held at 135F or above. Immediately discontinue storing PHF at room temperature., 114130-114130.5, 114132, 114133, 114137, 114139, 114153, 114163, 114165, 114167, 114169, 114175, 114177, 114180, 114182 - Ensure all equipment is approved, properly installed, clean, and maintained in good repair. Ensure all appliances are NSF-approved, commercial grade, durable, and easily cleanable., 114259, 114259.1, 114259.4, 114259.5 - Eliminate the infestation/activity of cockroaches/rodents/flies/vermin from the food facility by using only approved methods. Remove all evidence of the infestation and thoroughly clean and sanitize all affected surfaces. Construct, equip, maintain and operate the food facility so as to prevent the entrance and harborage of animals, birds and vermin including, but not limited to, rodents and insects., 114123, 114197, 114328(o) - Eliminate sewage backflow into the facility. Clean and sanitize all areas contaminated with sewage with a bleach solution (1 cup bleach per 9 cups water).Hire a licensed plumbing contractor if necessary. All contaminated food items must be discarded. All items that cannot be properly sanitized must be discarded., 114143(d), 114266, 114268, 114268.1, 114271, 114272 - Provide walls / ceilings using materials that are durable, smooth, nonabsorbent, light-colored, and washable surfaces. All floor surfaces, other than the customer service areas, shall be approved, smooth, durable, and made of nonabsorbent material that is easily cleanable. Approved base coving shall be provided in all areas, except customer service areas and where food is stored in original unopened containers. Food facilities shall be fully enclosed. All food facilities shall be kept clean and in good repair., 113967, 113976, 113980, 113988, 113990, 114035, 114254.3, 113975 - Discard all contaminated/adulterated food immediately if it bears or contains any poisonous or deleterious substance that may render it impure or injurious to health., - Food, equipment, or utensils that are found to be unsanitary or in disrepair may be Voluntarily Condemned and Destroyed by the person in charge.",
"violationCount": "7",
"businessName": "ZINGARI RISTORANTE",
"permitNumber": "29047",
"businessId": "",
"address": "501 POST ST",
"postalCode": "",
"neighborhood": "Tenderloin",
"district": "2",
"inspector": "John Wells",
"latitude": "37.78791300000100",
"longitude": "-122.4103950000020",
"groupKey": "",
"groupCount": ""
}

Source

Note: inspection results are SF's own public health ratings. A "Closure" result means the facility was closed at the time of that inspection; reasons are recorded in free-text violation notes rather than a structured field.