Looking for the overview — what this API returns, what it costs, and a call you can run without a key? See the Package Registries API page →
Developer Tools

Package Registries API & Scraper

The Package Registries API returns npm and PyPI package data as clean JSON.

7 actionsLive JSON1,000 free credits$0.67–$1.50 / 1,000 creditsMCP-ready
Get a free keyOpen in playground

🤖 Using an AI assistant? Copy this link into ChatGPT / Claude / Cursor — it reads every endpoint and parameter instantly and tells you if this API fits your use case.

The primary package endpoint returns a package's name, latest version, description, license, homepage, repository, keywords, maintainers and dependencies, and you can list versions, pull a specific version, resolve dependencies, read download stats, search and look up a maintainer. It is built for developer tools, dependency dashboards and supply-chain workflows that need normalized npm and PyPI metadata from one endpoint. One ReefAPI key, one shared credit pool, the standard envelope.

Reference

The same question, answered differently by npm and PyPI

One engine covers two registries, and they genuinely differ — not in our shaping, but in what each ecosystem publishes. registry is required on every action for that reason. Values below are measured from live calls on react, express and requests.

What you wantnpm returnsPyPI returns
the current versionthe dist-tag resolution — measured react 19.2.8the project version
release channelsdist_tags with seven channels measured on react: latest, next, canary, experimental, beta, rc, backportno equivalent — PyPI has no tag concept
dependenciesfour separate maps: dependencies, dev_dependencies, peer_dependencies, optional_dependenciesrequires_dist[] raw strings plus a parsed map
dependency valuessemver RANGES, not pinned versions — measured express: qs "^6.14.0", cookie "^0.7.1"PEP 508 specifiers, environment markers included
downloadsa count for the period you ask for, with start and endthree fixed windows at once — measured requests: last_day 42,760,091 · last_week 396,572,056 · last_month 1,804,395,908
download sourcethe registry's own countspypistats.org, named in an attribution field you should carry with the number
per-version extrasdist and enginesrequires_dist and classifiers

version_count on the package action tells you how deep the history goes — measured 2,920 for react — and versions pages through it. Note that published_at came back null on every measured npm version row, because the abbreviated registry document that keeps a 2,920-version response fetchable omits the release-date map. The same is why the package action's time object came back empty.

Live example

Real request and response JSON

Captured from the indexed primary action, search, on .

Captured request
{
  "method": "POST",
  "url": "https://api.reefapi.com/packages/v1/search",
  "headers": {
    "x-api-key": "$REEF_KEY",
    "content-type": "application/json"
  },
  "body": {
    "registry": "npm",
    "query": "fastapi"
  }
}
Captured response
{
  "ok": true,
  "meta": {
    "api": "packages",
    "endpoint": "search",
    "mode": "live",
    "latency_ms": 929.8,
    "record_count": 20,
    "bytes": 18608,
    "cache_hit": false,
    "registry": "npm",
    "query": "fastapi",
    "page": 1,
    "page_size": 20,
    "from": 0,
    "next_from": 20,
    "total": 1156,
    "has_more": true
  },
  "data": {
    "results": [
      {
        "registry": "npm",
        "name": "fastapi",
        "version": "0.0.8",
        "description": "A simple CLI utility for quickly creating Express-based servers with a single configuration file",
        "license": "ISC",
        "keywords": [
          "express",
          "api",
          "server"
        ],
        "maintainers": [
          {
            "email": "[trimmed-depth]",
            "username": "[trimmed-depth]"
          }
        ],
        "publisher": {
          "email": "[redacted-email]",
          "username": "timambler"
        },
        "date": "[redacted-phone]T16:12:09.755Z",
        "links": {
          "homepage": "https://github.com/tkambler/fastapi#readme",
          "repository": "git+https://github.com/tkambler/fastapi.git",
          "bugs": "https://github.com/tkambler/fastapi/issues",
          "npm": "https://www.npmjs.com/package/fastapi"
        },
        "score": {
          "final": 928.23816,
          "detail": {
            "popularity": "[trimmed-depth]",
            "quality": "[trimmed-depth]",
            "maintenance": "[trimmed-depth]"
          }
        },
        "search_score": 928.23816,
        "downloads": 2202,
        "flags": {
          "insecure": 0
        }
      },
      {
        "registry": "npm",
        "name": "fastapi-rtk",
        "version": "2.10.2",
        "description": "A React component library for FastAPI in combination with FastAPI React Toolkit backend, built with Mantine, JsonForms, and Zustand.",
        "license": "MIT",
        "keywords": [
          "fastapi",
          "react",
          "component"
        ],
        "maintainers": [
          {
            "email": "[trimmed-depth]",
            "username": "[trimmed-depth]"
          }
        ],
        "publisher": {
          "email": "[redacted-email]",
          "actor": {
            "name": "[trimmed-depth]",
            "type": "[trimmed-depth]",
            "email": "[trimmed-depth]"
          },
          "username": "dtacs"
        },
        "date": "[redacted-phone]T12:54:47.152Z",
        "links": {
          "npm": "https://www.npmjs.com/package/fastapi-rtk"
        },
        "score": {
          "final": 344.55225,
          "detail": {
            "popularity": "[trimmed-depth]",
            "quality": "[trimmed-depth]",
            "maintenance": "[trimmed-depth]"
          }
        },
        "search_score": 344.55225,
        "downloads": 6613,
        "flags": {
          "insecure": 0
        }
      },
      {
        "registry": "npm",
        "name": "@kernlang/fastapi",
        "version": "3.5.1",
        "description": "Kern FastAPI Python backend transpiler",
        "license": "AGPL-3.0",
        "keywords": [
          "kern",
          "llm",
          "fastapi"
        ],
        "maintainers": [
          {
            "email": "[trimmed-depth]",
            "username": "[trimmed-depth]"
          }
        ],
        "publisher": {
          "email": "[redacted-email]",
          "username": "cukasn"
        },
        "date": "[redacted-phone]T21:05:37.659Z",
        "links": {
          "npm": "https://www.npmjs.com/package/@kernlang/fastapi"
        },
        "score": {
          "final": 255.54477,
          "detail": {
            "popularity": "[trimmed-depth]",
            "quality": "[trimmed-depth]",
            "maintenance": "[trimmed-depth]"
          }
        },
        "search_score": 255.54477,
        "downloads": 660,
        "flags": {
          "insecure": 0
        }
      }
    ]
  }
}
Actions

What the Package Registries API does

ActionDescriptionConcrete use caseKey params
packagefull package metadata (latest version normalized)Platform and DevOps teams call package to get full package metadata (latest version normalized).registry, name
versionspaginated version list for a packageSecurity and supply-chain teams call versions to get paginated version list for a package.registry, name, page, page_size
versionsingle version metadataDeveloper-tool builders call version to get single version metadata.registry, name, version
dependenciesruntime + dev dependencies for a version (latest if omitted)AI-agent developers call dependencies to get runtime + dev dependencies for a version (latest if omitted).registry, name, version
downloadsdownload statistics (npm: period=last-day|week|month|year; pypi: recent day/week/month)Platform and DevOps teams call downloads to get download statistics (npm.registry, name, period
searchsearch packages (npm: registry API; pypi: libraries.io→HTML→ranked simple-index+enrich)Security and supply-chain teams call search to search packages (npm.registry, query, page, page_size, from
maintainermaintainer/author records for a packageDeveloper-tool builders call maintainer to get maintainer/author records for a package.registry, name
Code samples

Call search from your stack

curl -X POST https://api.reefapi.com/packages/v1/search \
  -H "x-api-key: $REEF_KEY" \
  -H "content-type: application/json" \
  -d '{"registry":"npm","query":"fastapi"}'
MCP one-liner
Ask your MCP-connected assistant: call reefapi.packages.search with {"registry":"npm","query":"fastapi"}.
Use cases

Who uses this API and why

  • Dependency dashboards call package and versions to track a library's releases and license.
  • Supply-chain tools use dependencies to map a package's full dependency tree.
  • Developer products use downloads and search to rank and compare packages by popularity.
FAQ

Questions developers ask before integrating

Is the `latest` dist-tag the newest version?

No — it is the version npm install gives you, which is deliberately not the newest thing published. A measured react lookup returned latest 19.2.8 while the same dist_tags object carried canary at 19.3.0-canary-a1124489-20260826 and experimental at 0.0.0-experimental-a1124489-20260826, both newer builds. Seven channels came back on that one package: latest, next, canary, experimental, beta, rc and backport. If you are building an out-of-date check, compare against latest, not against the top of the versions list.

Are the dependency values actual versions I can install?

No, they are semver ranges exactly as the author wrote them. A measured express lookup returned qs "^6.14.0", cookie "^0.7.1" and body-parser "^2.2.1" — carets, not pins. Nothing here resolves a dependency tree or reads a lockfile, so what you get is the declared intent, not what a given install would produce. That is the right input for licence and policy checks on declared dependencies, and the wrong input for reconstructing a specific build.

A package returned an empty dependencies object. Is that a fetch failure?

Usually not. Measured, react returned dependencies {} and dev_dependencies {} because it genuinely ships with no runtime dependencies — while express, fetched the same way, returned 28 runtime and 16 dev dependencies. An empty map is a real answer about the package. Cross-check with the dependencies action, which returns the four maps for a specific version, before you conclude anything went wrong.

Why do download numbers come back in a different shape per registry?

Because the two ecosystems publish different things. For PyPI you get last_day, last_week and last_month together in one response — measured on requests as 42.8 million, 396.6 million and 1.8 billion — sourced from pypistats.org and carrying an attribution string you are expected to keep with the figure. For npm you ask for a period and get a single count with its start and end dates. Do not build one chart that mixes the two without normalizing the window first.

Why is published_at null on version rows?

Because the registry document being read is the abbreviated one, which omits release dates. A measured versions call on react returned 2,920 total versions with published_at null on every row, and meta reported fetch_mode "abbreviated" so the reason is visible rather than hidden. The same omission is why the package action's time object came back as {}. Version strings, ordering and the latest flag are all present and reliable; dates are the thing to get elsewhere if you need them.

How do I page through a package with thousands of versions?

versions takes page and page_size, and meta returns page, page_size, total, has_more and next_page. Measured on react, total came back as 2,920 — a package with that much history is not something to pull in one call, and pre-release channels dominate the top of the list. If you only want stable releases, filter the version strings yourself: anything carrying canary, experimental, beta or rc in the string is a pre-release by npm convention.

Do I need registry credentials?

No. Both npm and PyPI publish this metadata openly, and neither needs an account, a token, or a rate-limit deal — you use your ReefAPI key and nothing else. That is the whole point of routing it through here: one key and one response envelope across two registries that otherwise have different hosts, different auth stories and different JSON shapes.

Can I search for packages rather than look one up?

Yes — search takes the registry plus a query and returns name, version, description, license, a relevance score and links or maintainers per hit, with paging in meta. The score is the registry's own relevance ranking, not a quality or popularity metric, so do not present it as one. If you want popularity, take the names from search and follow up with downloads.

What is the Package Registries API?

Package Registries API is a ReefAPI endpoint group for package registries It returns live JSON through POST requests under /packages/v1.

Is the Package Registries API free to try?

Yes. ReefAPI starts with 1,000 free credits, no card required. Package Registries calls use the same shared credit balance as every other ReefAPI engine.

Do I need a Package Registries login or account?

No login to Package Registries is needed for the API response. You call ReefAPI with your x-api-key header, and the playground can run live examples before you create a production key.

How fresh is the Package Registries data?

The page example is captured from a live package call, and production requests fetch live data through ReefAPI rather than a static sample.

How many credits does the Package Registries API use?

Package Registries actions currently cost 1-2 credits per successful call. Failed or blocked calls are free, and all APIs draw from one credit pool.

Can I call Package Registries from an AI assistant or MCP client?

Yes. Connect ReefAPI once through MCP and your assistant can call packages actions with the same key, credit pool and JSON envelope used by normal REST requests.

docs / packages

Package Registries

Package Registries

base /packages/v17 endpoints
post/packages/v1/package1 credit

full package metadata (latest version normalized)

ParameterAllowed / rangeDescription
registryrequirednpm · pypi · node · nodejs · python · pipWhich package registry to query. npm = Node.js packages; pypi = Python packages. (Synonyms node/nodejs -> npm, python/pip -> pypi.)
namerequiredExact package name (e.g. npm 'react', PyPI 'requests'). Scoped npm names like '@scope/pkg' are supported.
Try in playground →
post/packages/v1/versions1 credit

paginated version list for a package

ParameterAllowed / rangeDescription
registryrequirednpm · pypi · node · nodejs · python · pipWhich package registry to query. npm = Node.js packages; pypi = Python packages. (Synonyms node/nodejs -> npm, python/pip -> pypi.)
namerequiredExact package name (e.g. npm 'react', PyPI 'requests'). Scoped npm names like '@scope/pkg' are supported.
page = 1optional1–1-based page number for paginated lists (versions / search).
page_size = 50optional1–250Results per page (1-250, default 50). Larger values are clamped.
Try in playground →
post/packages/v1/version1 credit

single version metadata

ParameterAllowed / rangeDescription
registryrequirednpm · pypi · node · nodejs · python · pipWhich package registry to query. npm = Node.js packages; pypi = Python packages. (Synonyms node/nodejs -> npm, python/pip -> pypi.)
namerequiredExact package name (e.g. npm 'react', PyPI 'requests'). Scoped npm names like '@scope/pkg' are supported.
versionrequiredExact version string to fetch (e.g. '18.2.0', '2.31.0').
Try in playground →
post/packages/v1/dependencies1 credit

runtime + dev dependencies for a version (latest if omitted)

ParameterAllowed / rangeDescription
registryrequirednpm · pypi · node · nodejs · python · pipWhich package registry to query. npm = Node.js packages; pypi = Python packages. (Synonyms node/nodejs -> npm, python/pip -> pypi.)
namerequiredExact package name (e.g. npm 'react', PyPI 'requests'). Scoped npm names like '@scope/pkg' are supported.
versionoptionalOptional exact version; omit to use the latest published version.
Try in playground →
post/packages/v1/downloads1 credit

download statistics (npm: period=last-day|week|month|year; pypi: recent day/week/month)

ParameterAllowed / rangeDescription
registryrequirednpm · pypi · node · nodejs · python · pipWhich package registry to query. npm = Node.js packages; pypi = Python packages. (Synonyms node/nodejs -> npm, python/pip -> pypi.)
namerequiredExact package name (e.g. npm 'react', PyPI 'requests'). Scoped npm names like '@scope/pkg' are supported.
period = last-monthoptionallast-day · last-week · last-month · last-yearnpm download window (rejects unknown values). Ignored for PyPI, which always returns recent last-day/last-week/last-month totals.
Try in playground →
post/packages/v1/maintainer1 credit

maintainer/author records for a package

ParameterAllowed / rangeDescription
registryrequirednpm · pypi · node · nodejs · python · pipWhich package registry to query. npm = Node.js packages; pypi = Python packages. (Synonyms node/nodejs -> npm, python/pip -> pypi.)
namerequiredExact package name (e.g. npm 'react', PyPI 'requests'). Scoped npm names like '@scope/pkg' are supported.
Try in playground →