# Uk Ons Statistics Scraper (`b2b_lead_generation/uk-ons-statistics-scraper`) Actor

Extract datasets, metadata, and latest version links from Office for National Statistics data. Easily browse catalogues, search specific dataset IDs, and export structured results as JSON, CSV, or Excel directly from your dataset.

- **URL**: https://apify.com/b2b_lead_generation/uk-ons-statistics-scraper.md
- **Developed by:** [B2B Lead Generation](https://apify.com/b2b_lead_generation) (community)
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $2.99 / 1,000 results

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.
Since this Actor supports Apify Store discounts, the price gets lower the higher subscription plan you have.

Learn more: https://docs.apify.com/actors/running/actors-in-store.md#pay-per-event

## What's an Apify Actor?

An Actor is a serverless cloud program that runs on the Apify platform. It has two run modes.
In Batch mode, an Actor accepts a well-defined JSON input, performs an action which can take anything from a few seconds to a few hours,
and optionally produces a well-defined JSON output, datasets with results, or files in key-value store.
In Standby mode, an Actor provides a web server which can be used as a website, API, or an MCP server.

Apify vocabulary and the platform model are defined once, in the agent quickstart at https://apify.com/agents.md.

## How to integrate an Actor?

If asked about integration, you help developers integrate Actors into their projects.
You adapt to their stack and deliver integrations that are safe, well-documented, and production-ready.

Do not guess an integration path. Every one of them is in the agent quickstart at https://apify.com/agents.md: the Apify MCP server, Agent Skills with the Apify CLI, the JavaScript and Python clients, the REST API, and the account-free path for an agent with no human to sign in. It also carries the rule on stating cost before the first paid run.

For examples already wired to this Actor's own input schema, see the [API](#api) section below.

Each client library has reference documentation the quickstart does not restate: [JavaScript/TypeScript](https://docs.apify.com/api/client/js/docs.md) (`npm install apify-client`) and [Python](https://docs.apify.com/api/client/python/docs.md) (`pip install apify-client`).

# README

## UK ONS Statistics Scraper: Datasets and Observations

<p align="center">
  <img src="https://imgur.com/EHPGBQ1.png" alt="Uk Ons Statistics" style="max-width:100%; border-radius:14px; width:680px;" />
</p>

Extract structured statistical datasets from the Office for National Statistics catalogue. Easily gather dataset lists, descriptions, contact information, and version details. Export your clean results directly to JSON, CSV, or Excel on Apify.

***

### Key Features & Use Cases

- **Catalogue Archiving:** Save dataset titles, topics, keywords, and release notes for ongoing research and data archives.
- **Price Index & Metric Lookup:** Fetch CPIH or other key dataset descriptions, contact info, and current version details.
- **Scheduled Data Syncs:** Set your run on a timer to track ongoing updates and identify fresh releases.
- **Version Tracking:** Keep track of updated dataset version identifiers as new publications drop.
- **Metadata & Licence Review:** Keep licence strings, methodologies, and source links conveniently organised alongside dataset items.

***

### What Data Does This Actor Extract?

Each processed item yields a clean document record. Key extracted attributes include:

- `datasetTitle` & `datasetDescription`: Formatted text fields for clear organization.
- `id`: Unique identifier for each dataset.
- `contacts`: Official department contact details (names, emails, telephone lines).
- `keywords`: Related thematic tags.
- `last_updated`: Timestamp of the latest publication refresh.
- `next_release` & `release_frequency`: Details on publication schedules.
- `national_statistic`: Indicates official statistical designation.
- `edition` & `versionId`: Version details attached to the record.
- `scrapedAt`: Timestamp recording when the row was saved.

***

### Input Options

| Parameter | Type | Default | Description |
| :--- | :--- | :--- | :--- |
| `mode` | String | `datasets` | Options: `datasets` (list datasets) or `versions` (check version details). |
| `datasetId` | String | `""` | Target dataset identifier (e.g., `cpih01`). Leave empty to list the catalogue. |
| `edition` | String | `"time-series"` | Targeted edition variant inside version details. |
| `version` | String | `"latest"` | Target version label (`latest` or exact version number). |
| `maxItems` | Integer | `100` | Maximum rows to collect (capped at 1000). |
| `requestDelaySecs` | Number | `0.75` | Pause between outgoing queries (0.5 to 1.0 second). |
| `timeoutSecs` | Integer | `300` | Total run time limit in seconds. |
| `requestTimeoutSecs` | Integer | `30` | Per-request timeout limit in seconds. |
| `proxyConfiguration` | Object | `{ "useApifyProxy": false }` | Optional proxy settings object. |

#### Input Examples

**Catalogues Scan:**

```json
{
    "mode": "datasets",
    "datasetId": "",
    "edition": "time-series",
    "version": "latest",
    "maxItems": 100,
    "requestDelaySecs": 0.75,
    "timeoutSecs": 300,
    "requestTimeoutSecs": 30,
    "proxyConfiguration": { "useApifyProxy": false }
}

```

**Single Dataset Detail:**

```json
{
    "mode": "versions",
    "datasetId": "cpih01",
    "edition": "time-series",
    "version": "latest",
    "maxItems": 1
}

```

***

### Output Example

```json
{
    "contacts": [
        {
            "email": "qualityoflife@ons.gov.uk",
            "name": "Will Shufflebottom, Owain Birrell, Pavan Bains and Geeta Kerai",
            "telephone": "+44 300 0671543"
        }
    ],
    "datasetDescription": "Seasonally and non seasonally-adjusted quarterly estimates of life satisfaction.",
    "keywords": ["well-being"],
    "id": "wellbeing-quarterly",
    "last_updated": "2023-12-13T09:40:24.204Z",
    "national_statistic": false,
    "next_release": "TBC",
    "release_frequency": "Quarterly",
    "state": "published",
    "datasetTitle": "Quarterly personal well-being estimates",
    "edition": "time-series",
    "versionId": "9",
    "mode": "datasets",
    "scrapedAt": "2026-10-12T00:00:00Z"
}

```

***

### How It Works

1. Parses your configuration, setting your row limits and request delays.
2. Formats and sends queries for either catalogue indexes or individual target items.
3. Formats incoming statistical records, drops duplicates, and safely handles missing items without breaking your batch run.
4. Concludes automatically when your item target, timeout limit, or dataset end is reached.

***

### FAQ

**Can this actor download raw observation values directly?**

No. It focuses on dataset catalogue records, descriptions, metadata, and version references.

**What happens if I pass an invalid dataset ID?**

An error record is logged with status details so your workflow continues smoothly without crashing.

**Why did my run return zero rows?**

An empty catalogue response saves zero rows and writes an explicit confirmation note in the log.

***

### Trademark Notice

UK ONS Statistics and related names, logos, and marks belong to their respective owners. Mentioning them here serves purely to describe the dataset content and implies no endorsement, partnership, or direct association.

***

### Is web scraping legal?

This tool collects publicly accessible information. When storing or processing dataset results, keep the following guidelines in mind:

- **Personal Data:** Some statistical entries list departmental contact names, phone numbers, or email addresses. Please comply with relevant data handling guidelines (such as GDPR or local regulations) if processing or resharing these details.
- **Copyright & Terms:** Ensure you adhere to Open Government Licence guidelines and respect attribution requirements when using third-party content.
- **General Disclaimer:** This documentation provides factual overview information rather than formal legal advice.

# Actor input Schema

## `mode` (type: `string`):

datasets lists the catalogue. versions keeps the same dataset documents and reads the latest version link already embedded in each one.

## `datasetId` (type: `string`):

ONS dataset id such as cpih01. Leave empty to page through the public dataset list.

## `edition` (type: `string`):

Edition name expected inside the latest version link, usually time-series. Used in versions mode. The actor does not call a separate editions URL.

## `version` (type: `string`):

latest, or a version number that must match the latest version id already returned on the dataset. Other version URLs are not requested.

## `maxItems` (type: `integer`):

Maximum rows to save in one run, including error rows. Values above 1000 are clamped to 1000.

## `requestDelaySecs` (type: `number`):

Seconds to wait between HTTP calls. Kept between 0.5 and 1 so the run stays near one to two requests per second.

## `timeoutSecs` (type: `integer`):

Stop scheduling new requests after this many seconds. Rows already saved are kept.

## `requestTimeoutSecs` (type: `integer`):

Per-request timeout in seconds for each call to the ONS beta API.

## `proxyConfiguration` (type: `object`):

Optional proxy. Default is no proxy. The public ONS API does not require a proxy, and proxies are not used to get around stated limits.

## Actor input object example

```json
{
  "mode": "datasets",
  "datasetId": "cpih01",
  "edition": "time-series",
  "version": "latest",
  "maxItems": 100,
  "requestDelaySecs": 0.75,
  "timeoutSecs": 300,
  "requestTimeoutSecs": 30,
  "proxyConfiguration": {
    "useApifyProxy": false
  }
}
```

# Actor output Schema

## `datasetUrl` (type: `string`):

Default dataset for this run.

## `overview` (type: `string`):

Table of dataset rows from this run.

# API

You can run this Actor programmatically using our API. Below are code examples in JavaScript, Python, and CLI, as well as the OpenAPI specification and MCP server setup.

## JavaScript example

```javascript
import { ApifyClient } from 'apify-client';

// Initialize the ApifyClient with your Apify API token
// Replace the '<YOUR_API_TOKEN>' with your token
const client = new ApifyClient({
    token: '<YOUR_API_TOKEN>',
});

// Prepare Actor input
const input = {
    "mode": "datasets",
    "datasetId": "",
    "edition": "time-series",
    "version": "latest",
    "maxItems": 100,
    "requestDelaySecs": 0.75,
    "timeoutSecs": 300,
    "requestTimeoutSecs": 30,
    "proxyConfiguration": {
        "useApifyProxy": false
    }
};

// Run the Actor and wait for it to finish
const run = await client.actor("b2b_lead_generation/uk-ons-statistics-scraper").call(input);

// Fetch and print Actor results from the run's dataset (if any)
console.log('Results from dataset');
console.log(`💾 Check your data here: https://console.apify.com/storage/datasets/${run.defaultDatasetId}`);
const { items } = await client.dataset(run.defaultDatasetId).listItems();
items.forEach((item) => {
    console.dir(item);
});

// 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/js/docs

```

## Python example

```python
from apify_client import ApifyClient

# Initialize the ApifyClient with your Apify API token
# Replace '<YOUR_API_TOKEN>' with your token.
client = ApifyClient("<YOUR_API_TOKEN>")

# Prepare the Actor input
run_input = {
    "mode": "datasets",
    "datasetId": "",
    "edition": "time-series",
    "version": "latest",
    "maxItems": 100,
    "requestDelaySecs": 0.75,
    "timeoutSecs": 300,
    "requestTimeoutSecs": 30,
    "proxyConfiguration": { "useApifyProxy": False },
}

# Run the Actor and wait for it to finish
run = client.actor("b2b_lead_generation/uk-ons-statistics-scraper").call(run_input=run_input)

# Fetch and print Actor results from the run's dataset (if there are any)
print(f"💾 Check your data here: https://console.apify.com/storage/datasets/{run.default_dataset_id}")
for item in client.dataset(run.default_dataset_id).iterate_items():
    print(item)

# 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/python/docs/quick-start

```

## CLI example

```bash
echo '{
  "mode": "datasets",
  "datasetId": "",
  "edition": "time-series",
  "version": "latest",
  "maxItems": 100,
  "requestDelaySecs": 0.75,
  "timeoutSecs": 300,
  "requestTimeoutSecs": 30,
  "proxyConfiguration": {
    "useApifyProxy": false
  }
}' |
apify call b2b_lead_generation/uk-ons-statistics-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,b2b_lead_generation/uk-ons-statistics-scraper"
        }
    }
}
```

The hosted server signs you in with OAuth on first connect, so no API token belongs in this config. Clients without OAuth support can send an `Authorization: Bearer <APIFY_API_TOKEN>` header instead, using a token from API & Integrations in Apify Console (https://console.apify.com/settings/integrations).

## OpenAPI specification

Download the OpenAPI definition: https://api.apify.com/v2/actors/2uuOyaAjcovduduLk/builds/Bd45jWOyNCG9uF6QF/openapi.json
