DEV Community

Alex Spinov
Alex Spinov

Posted on

PyPI Has a Secret JSON API — Analyze Any Python Package Without Installing It

PyPI — the Python Package Index — has a free JSON API that nobody talks about. You can look up any package's metadata, downloads, dependencies, and version history without installing anything.

No API key. No rate limits. Just HTTP requests.

The PyPI JSON API

Every package on PyPI has a public JSON endpoint:

https://pypi.org/pypi/{package_name}/json
Enter fullscreen mode Exit fullscreen mode

That is it. No auth, no signup, no tokens.

What You Can Extract

1. Package Metadata

import urllib.request
import json

def get_package(name):
    url = f"https://pypi.org/pypi/{name}/json"
    resp = urllib.request.urlopen(url)
    return json.loads(resp.read())

pkg = get_package("requests")
info = pkg["info"]
print(f"Name: {info['name']}")
print(f"Version: {info['version']}")
print(f"Summary: {info['summary']}")
print(f"Author: {info['author']}")
print(f"License: {info['license']}")
print(f"Home page: {info['home_page']}")
print(f"Requires Python: {info['requires_python']}")
Enter fullscreen mode Exit fullscreen mode

Output:

Name: requests
Version: 2.31.0
Summary: Python HTTP for Humans.
Author: Kenneth Reitz
License: Apache-2.0
Enter fullscreen mode Exit fullscreen mode

2. Download Stats (via pypistats.org)

PyPI itself does not expose download counts, but pypistats.org does:

def get_downloads(name):
    url = f"https://pypistats.org/api/packages/{name}/recent"
    resp = urllib.request.urlopen(url)
    data = json.loads(resp.read())
    return data["data"]

stats = get_downloads("fastapi")
print(f"Last day: {stats['last_day']:,}")
print(f"Last week: {stats['last_week']:,}")
print(f"Last month: {stats['last_month']:,}")
Enter fullscreen mode Exit fullscreen mode

3. Dependency Analysis

def get_dependencies(name):
    pkg = get_package(name)
    deps = pkg["info"].get("requires_dist", []) or []
    required = [d for d in deps if "; extra" not in d]
    optional = [d for d in deps if "; extra" in d]
    return {"required": required, "optional": optional}

deps = get_dependencies("fastapi")
print(f"Required: {len(deps['required'])} packages")
for d in deps["required"]:
    print(f"  - {d}")
Enter fullscreen mode Exit fullscreen mode

4. Version History Timeline

def version_timeline(name):
    pkg = get_package(name)
    releases = pkg["releases"]
    versions = []
    for ver, files in releases.items():
        if files:
            date = files[0]["upload_time"][:10]
            versions.append((date, ver))
    return sorted(versions, reverse=True)[:10]

for date, ver in version_timeline("django"):
    print(f"{date}: v{ver}")
Enter fullscreen mode Exit fullscreen mode

5. Competitor Comparison Tool

This is where it gets powerful. Compare any two packages side by side:

def compare(pkg1, pkg2):
    a = get_package(pkg1)["info"]
    b = get_package(pkg2)["info"]

    sa = get_downloads(pkg1)
    sb = get_downloads(pkg2)

    print(f"{'':15} | {pkg1:>15} | {pkg2:>15}")
    print(f"{'-'*15}-+-{'-'*15}-+-{'-'*15}")
    print(f"{'Version':15} | {a['version']:>15} | {b['version']:>15}")
    print(f"{'Monthly DLs':15} | {sa['last_month']:>15,} | {sb['last_month']:>15,}")
    print(f"{'License':15} | {str(a.get('license','?'))[:15]:>15} | {str(b.get('license','?'))[:15]:>15}")

compare("flask", "fastapi")
Enter fullscreen mode Exit fullscreen mode

Real Use Cases

Market research: Which ML framework is growing fastest? Compare download trends of torch vs tensorflow vs jax.

Security audit: Check if a package has been updated recently. Abandoned packages = security risk.

Dependency risk: How many dependencies does your dependency have? Deep dependency trees = fragile builds.

Competitive intelligence: Track how many packages depend on your competitor vs you.

Full Script: PyPI Package Analyzer

I built a complete tool that wraps all of this into a CLI:

#!/usr/bin/env python3
"""PyPI Package Analyzer — Analyze any Python package without installing it."""

import json, sys, urllib.request

def analyze(name):
    pkg_url = f"https://pypi.org/pypi/{name}/json"
    stats_url = f"https://pypistats.org/api/packages/{name}/recent"

    pkg = json.loads(urllib.request.urlopen(pkg_url).read())
    info = pkg["info"]

    try:
        stats = json.loads(urllib.request.urlopen(stats_url).read())["data"]
    except Exception:
        stats = {"last_day": "?", "last_week": "?", "last_month": "?"}

    deps = info.get("requires_dist", []) or []
    versions = len(pkg.get("releases", {}))

    print(f"Package: {info['name']} v{info['version']}")
    print(f"Summary: {info['summary']}")
    print(f"Author: {info['author']}")
    print(f"License: {info.get('license', 'Unknown')}")
    print(f"Python: {info.get('requires_python', 'Any')}")
    print(f"Downloads (month): {stats.get('last_month', '?'):,}" if isinstance(stats.get('last_month'), int) else f"Downloads: {stats.get('last_month', '?')}")
    print(f"Total versions: {versions}")
    print(f"Dependencies: {len([d for d in deps if '; extra' not in d])} required, {len([d for d in deps if '; extra' in d])} optional")

if __name__ == "__main__":
    analyze(sys.argv[1] if len(sys.argv) > 1 else "requests")
Enter fullscreen mode Exit fullscreen mode

Save as pypi_analyzer.py and run:

python pypi_analyzer.py fastapi
python pypi_analyzer.py django
python pypi_analyzer.py langchain
Enter fullscreen mode Exit fullscreen mode

What Python packages would you analyze first? I am building a dashboard that tracks package trends over time — drop a comment if you would use it.

Full code: pypi-package-analyzer on GitHub — clone it and start analyzing.

I build data collection tools for teams that need market intelligence. See my other tools or email me.

Top comments (0)