UK Food Hygiene Ratings Scraper (FHRS / FSA Data)
Pricing
from $4.00 / 1,000 establishment delivereds
UK Food Hygiene Ratings Scraper (FHRS / FSA Data)
Extract UK food establishment hygiene ratings from the Food Standards Agency open-data API: rating, scheme, local authority and business details. For food-safety due diligence, site checks and compliance dashboards. Filter by authority and minimum rating. No browser, no login.
Pricing
from $4.00 / 1,000 establishment delivereds
Rating
0.0
(0)
Developer
Steadfetch
Maintained by CommunityActor stats
0
Bookmarked
2
Total users
1
Monthly active users
an hour ago
Last modified
Categories
Share
steadfetch/uk-food-hygiene-monitor
Extract UK food establishment hygiene ratings from the official Food Standards Agency open data API. Structured JSON, no browser, no login, no CAPTCHA.
What it does
The Actor queries the FSA /Establishments API (version 2) and returns one dataset item per food business, with its current rating, rating date, business type, published address, local authority and coordinates.
- Filter by local authority (one or more names, comma-separated).
- Filter by minimum rating (0-5).
- Choose the FHRS (England, Wales, Northern Ireland) or FHIS (Scotland) scheme.
- Cap the number of results with
maxResults.
Every item is validated against the schema in .actor/dataset_schema.json before it reaches the dataset. With strictSchema: true (the default) an invalid item fails the run instead of being pushed.
The FSA publishes this data under the Open Government Licence v3.0. The API is free and needs no registration. The Actor does not scrape the ratings website and never returns personal contact data: it only extracts business premises information that the FSA already publishes.
Minimum input
{ "region": "Camden", "maxResults": 10 }
All fields are optional: an empty region queries every local authority, bounded by maxResults (default 100 — a useful first sample that finishes in seconds and stays well inside the Apify free plan; raise it for bulk pulls). minRating (0-5) keeps only numeric FHRS ratings at or above the value; schemeType selects FHRS (default, England/Wales/NI) or FHIS (Scotland).
Output fields
fhrs_id— establishment identifier.business_name,business_type— premises name and type, e.g.Restaurant/Cafe/Canteen.rating_value— published rating:0-5,Pass,Improvement Required,AwaitingInspection,AwaitingPublicationorExempt.rating_date— date of the rating.address_line,postal_code,local_authority_name— location as published by the FSA.latitude,longitude— premises coordinates.url,titleandscrapedAt— public FSA ratings page and envelope. Business premises only: no individual contact data.
Example output
{"url": "https://ratings.food.gov.uk/business/1824267","title": "1 REBEL","scrapedAt": "2026-10-19T18:00:00.000Z","fhrs_id": "1824267","business_name": "1 REBEL","business_type": "Restaurant/Cafe/Canteen","address_line": "1 REBEL, Lancing Street, London","postal_code": "NW1 1NA","local_authority_name": "Camden","rating_value": "5","rating_date": "2026-03-18","latitude": 51.528421,"longitude": -0.1314354}
Input
{"region": "Camden","minRating": 4,"schemeType": "FHRS","maxResults": 1000}
| Field | Type | Description |
|---|---|---|
region | string | One or more FSA local-authority names, comma-separated. Empty queries every authority (bounded by maxResults). |
minRating | integer 0-5 | Exclude lower numeric ratings. Non-numeric values such as AwaitingInspection are excluded when set. Applies to FHRS only; FHIS uses Pass / Improvement Required, so omit it for FHIS. |
schemeType | FHRS or FHIS | Default FHRS. Scottish authorities publish FHIS; the rest of the UK publishes FHRS. |
maxResults | integer | Default 100, maximum 20000. |
strictSchema | boolean | Default true; fail the run on schema violations. |
Project structure
.actor/actor.json Actor definition (payPerEvent, dataset schema, output schema).actor/input_schema.json INPUT options (region, minRating, schemeType, maxResults).actor/dataset_schema.json Item JSON Schema (fields) + table view for the Store.actor/pay_per_event.json PPE pricing (two synthetic platform events)src/fetch.ts FSA HTTP client: pagination, timeouts, retry/backoffsrc/extract.ts Pure parsing and filtering (fixture-tested, no network)src/main.ts Entry point: fetch, validate, pushsrc/validate-output.ts Ajv validator shared by the run and the teststest/ Offline fixtures and Vitest suites
Pay-per-event pricing
The Actor uses Apify pay-per-event pricing with the two synthetic platform events:
| Event | Charged when | Price |
|---|---|---|
apify-actor-start | a run starts (synthetic, automatic) | 0.00005 USD per run (Apify-recommended default; includes 5 seconds of free compute) |
apify-default-dataset-item | an establishment is saved to the dataset (synthetic, automatic) | 0.004 USD per result = 4.00 USD per 1,000 results |
There is no custom per-item event and no Actor.charge() call: the platform already charges apify-default-dataset-item per pushed item, so adding another event would bill users twice.
The price sits in the middle of the direct-competitor band (2.5-8 USD per 1,000) and inside Steadfetch's 1-10 USD band.
Measured cost per 1,000 results: a local run over the live FSA API (region: "Camden", maxResults: 1000) delivered 1,000 schema-valid items in 6.8 seconds using the 256 MB minimum memory allocation. At Apify's $0.20 per compute unit (1 CU = 1 GB-hour), that is 0.00047 CU = $0.0001 per 1,000 results; even with a conservative allowance for startup, dataset storage and data transfer the cost stays below $0.001 per 1,000 results. Margin over measured cost is above 99%.
Works on the Apify free plan — about 1,249 establishments for the $5 monthly credit ((5.00 USD − 0.0002 USD run-start at the default 4 GB memory) ÷ 0.004 USD per result).
Development
npm installnpm test # lint + typecheck + offline Vitest suites (no credit)npm run publish:check # Steadfetch publish gatenpm run schemas:validatenpm run smoke # local Apify run (no platform credit)
The test suite runs entirely against committed JSON fixtures captured from the real FSA API on 2026-10-19. A live run only needs the public API; no token is required.
FAQ
Do I need an FSA account or API key? No. The FSA open data API is free and needs no registration.
Does it need a browser? No. The FSA returns JSON, so the Actor uses plain HTTP. That is roughly 10x cheaper than a browser-based Actor.
Does it return personal data? No. The Actor only returns business premises fields already published by the FSA. It does not return phone numbers, email addresses or any individual's data.
When am I charged?
Once per run start (apify-actor-start) and once per valid result saved to the dataset (apify-default-dataset-item). Failed requests, retries and empty pages are not charged per result.
Is the output schema stable?
Yes. New fields are additive and the required fields in .actor/dataset_schema.json do not change.
Maintenance
This Actor is tested daily: automated runs check that the FSA API is reachable and that the output still matches the published schema. Failures are reported as issues in the Steadfetch Actors repository.