Skip to main content

neudata-api-client

A Python client for the Neudata Developer API. It lets you search and retrieve dataset metadata, additional datasets, filters, and DDQs — and ships with resilient defaults: it retries dropped connections, backs off and honours Retry-After on rate limits (429), and auto-paginates list endpoints.

Installation

pip install neudata-api-client

For development (using uv):

git clone https://github.com/neudata/neudata-api-client
cd neudata-api-client
uv sync

Authentication

The API authenticates with two headers, Email and Api-Token. Your token is available at https://www.neudata.co/users/edit.

Provide them via environment variables (recommended):

export NEUDATA_EMAIL="you@example.com"
export NEUDATA_API_TOKEN="your-api-token"

…or pass them directly to the client:

from neudata import NeudataClient

client = NeudataClient(email="you@example.com", api_token="your-api-token")

A .env.example is included as a template.

Quickstart

from neudata import NeudataClient

with NeudataClient() as client:
    # Search a single page of datasets
    results = client.search_datasets(q="satellite", per_page=10)

    # Or iterate over *every* matching dataset (pagination handled for you)
    for dataset in client.iter_datasets(equity_region=["uk", "europe"]):
        print(dataset["id"], dataset["title"])

    # Fetch the full detail record for one dataset
    detail = client.get_dataset(1234)

API reference

Method Endpoint Description
search_datasets(**filters) GET /datasets One page of dataset search results
iter_datasets(per_page=99, **filters) GET /datasets Iterate all datasets across pages
get_dataset(id) GET /datasets/{id} Full dataset detail
list_filters() GET /filters Available filter parameter names
get_filter_options(name) GET /filters/{name} Allowable options for a filter
search_additional_datasets(**filters) GET /additional-datasets One page of additional datasets
iter_additional_datasets(per_page=99, **filters) GET /additional-datasets Iterate all additional datasets
get_additional_dataset(id) GET /additional-datasets/{id} Full additional-dataset detail
list_ddqs(page, per_page) GET /ddqs List DDQs (Sentry subscribers)
iter_ddqs(per_page=99) GET /ddqs Iterate all DDQs
get_ddq(id) GET /ddqs/{id} DDQ detail + 10-minute download URL

Filters

Search methods accept the documented query parameters as keyword arguments, e.g. q, page, per_page, sort, sort_by, source, from_date, data_provider_id, and the array filters equity_region, asset_class, combined_dataset_types, frequency, history, subscription_price, report_type, feed_type, output_format, esg_topics, filter_labels, ticker_indices, and more.

Array filters are passed as Python lists and serialized into the repeated name[] form the API expects:

client.search_datasets(asset_class=["public-equity", "fixed-income"])
# -> GET /datasets?asset_class[]=public-equity&asset_class[]=fixed-income

Use client.list_filters() and client.get_filter_options(name) to discover the valid values for each filter at runtime.

Resilience: retries, backoff & rate limits

The client is configured on construction:

NeudataClient(
    timeout=30,                  # per-request timeout (seconds)
    max_retries=5,               # retries for dropped connections / 5xx
    backoff_factor=0.5,          # exponential backoff base
    max_backoff=60,              # cap on any single backoff sleep
    max_rate_limit_retries=10,   # retries specifically for 429 responses
    requests_per_minute=90,      # client-side throttle (0 disables it)
)
  • Dropped/closed connections (and timeouts and 5xx server errors) are retried up to max_retries times with jittered exponential backoff.
  • 429 rate limits are retried up to max_rate_limit_retries times. The Retry-After header is honoured when present; otherwise exponential backoff is used. When retries are exhausted a RateLimitError is raised.
  • A built-in client-side throttle keeps the sustained request rate below requests_per_minute (the API guideline is ~100/min) so bulk jobs avoid tripping the limiter in the first place.

Enable logging to see retry/backoff activity:

import logging
logging.getLogger("neudata").setLevel(logging.INFO)

Exceptions

All exceptions derive from neudata.NeudataError:

  • AuthenticationError401/403 (bad credentials; not retried)
  • NotFoundError404
  • RateLimitError429 retries exhausted (carries retry_after)
  • NeudataAPIError — other unexpected API responses (carries status_code, response_body)

Example: download the whole catalogue

A console script is installed with the package:

# Dump all datasets + additional datasets to neudata_export.json
neudata-download

# Custom output, only datasets, with full per-item detail records
neudata-download --output datasets.json --datasets-only --details

# Filter by date or free text
neudata-download --from-date 2026-01-01 --query "credit card"

Run neudata-download --help for all options. A minimal, readable version using the library directly is in examples/download_all.py:

python examples/download_all.py out.json

The output JSON has the shape:

{
  "datasets": [ ... ],
  "additional_datasets": [ ... ]
}

Development

uv sync             # create the venv and install deps + dev tools
uv run pytest       # run the test suite (no network calls)

Tests use responses to mock the API and a monkeypatched sleep, so they run instantly and offline.

There is also an opt-in live smoke test that hits every endpoint against the real API. It is excluded from the default run and requires credentials:

export NEUDATA_EMAIL="you@example.com"
export NEUDATA_API_TOKEN="your-api-token"
uv run pytest -m smoke -v      # hits the real Neudata API

(The DDQ checks skip automatically if your account isn't a Sentry subscriber.)

Releasing to PyPI

uv build                          # build sdist + wheel into dist/
uvx twine check dist/*            # validate metadata / long description

# Test upload first
uv publish --publish-url https://test.pypi.org/legacy/ --token "$TEST_PYPI_TOKEN"

# Then the real thing
uv publish --token "$PYPI_TOKEN"

License

MIT

Release files for neudata-api-client 0.2.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for neudata-api-client 0.2.0
File Size Uploaded
neudata_api_client-0.2.0.tar.gz 11.4 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for neudata-api-client 0.2.0
File Interpreter ABI Platform
neudata_api_client-0.2.0-py3-none-any.whl Python 3 none any Details

Total release size: 25.8 kB

Release files / neudata_api_client-0.2.0.tar.gz

Download URL neudata_api_client-0.2.0.tar.gz
Size 11.4 kB
Tags Source
SHA-256 checksum
How to use checksums
fcea3504e5002c5d3c78a4c63a37e892c201dff160be30ffe0b7f85eac07214b
BLAKE2b-256 checksum
How to use checksums
769d4685d16ec258fdd22cd33822a4ab45dfafbeb9562bfc26b9f8a9c53391e4
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via uv/0.8.2

Release files / neudata_api_client-0.2.0-py3-none-any.whl

Download URL neudata_api_client-0.2.0-py3-none-any.whl
Size 14.4 kB
Tags Python 3
SHA-256 checksum
How to use checksums
4f620f613d3212eb12435f4cc67bc64656a5d1f51583305691098596420ddc01
BLAKE2b-256 checksum
How to use checksums
52ed96c7193516c9d7a6dbb907c08bc927a60d1497db1b0ae087d3a41b14785c
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via uv/0.8.2

Release history Release notifications | RSS feed

This release

0.2.0 This release

2 release files

0.1.0

2 release files

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page