App Store market data for your code and your agents.
Every chart, estimate and keyword on AppleCharts is published each morning as plain JSON. Fetch it from anywhere, or connect the MCP server and ask in plain English. It’s free and needs no key.
- Apps tracked
- ≈15,000
- Countries
- 14
- Charts a day
- 680
- Rank history
- 90 days
Fetch the JSON
Files live under https://www.applecharts.com/data/snapshot/. They’re static, cached at the edge and served with open CORS, so they work from a browser, a script or a serverless function. The snapshot is replaced once a day; check manifest.generatedAt for its age.
manifest.json | Snapshot date, the countries collected, coverage (charts fetched and failed), methodology and warnings. Read it first. |
|---|---|
apps-index.json | One compact row per tracked app: name, developer, category, price, rating, ratings count, US ranks, countries charted, 7-day movement, revenue and download estimates with ranges and confidence. |
apps/{appId mod 64}.json | Full records: best rank per country and chart, the basis behind each estimate, tracked keywords the app ranks for. |
charts/{country}.json | Ordered app IDs for every collected chart: free, paid, grossing, and per category as grossing:6014 and so on. |
history/{country}.json | Up to 90 days of daily overall ranks per app and chart. |
keywords.json | Tracked US keywords with popularity, difficulty, opportunity and the top 10 apps for each. |
Countries: us jp gb kr de ca au fr it es nl br mx in.
curl -s https://www.applecharts.com/data/snapshot/charts/us.json \
| jq '.charts.grossing.ids[:10]'// Every tracked app, as compact rows.
const res = await fetch("https://www.applecharts.com/data/snapshot/apps-index.json")
const { fields, rows } = await res.json()
const apps = rows.map(r => Object.fromEntries(fields.map((f, i) => [f, r[i]])))
// Indie hits: earning $10K+/mo with fewer than 10K ratings.
const indie = apps
.filter(a => a.revenue >= 10_000 && a.ratingCount < 10_000)
.sort((a, b) => b.revenue - a.revenue)// Full record for one app (ranks per country, estimate basis, keywords).
const id = "1234567890"
const shard = BigInt(id) % 64n
const { apps } = await (await fetch(`https://www.applecharts.com/data/snapshot/apps/${shard}.json`)).json()
const app = apps.find(a => a.id === id)Connect an agent
The MCP server gives Claude, Cursor, Codex or any MCP client ten tools. The first six answer from the daily snapshot in milliseconds; the last four call Apple live for search, listings and reviews.
- Clone the repo and run
pnpm install(Node 22 or newer). - Add the server to your client’s MCP config, using your clone’s path.
- Ask something like “Find Health & Fitness apps earning over $10K a month with under 10K ratings, then read reviews of the top three.”
git clone https://github.com/shawn14/apple-charts.git
cd apple-charts && pnpm install --frozen-lockfile{
"mcpServers": {
"applecharts": {
"command": "pnpm",
"args": [
"--dir",
"/absolute/path/to/apple-charts",
"-s",
"mcp"
]
}
}
}| MCP tool | HTTP path | What it does |
|---|---|---|
discover_apps | /v1/discover | Filter and sort apps by country, chart, category, price, estimated revenue and downloads, ratings, release date and 7-day movement. |
top_charts | /v1/charts | Read a country’s Free, Paid or Grossing chart, overall or for one category. |
regional_hits | /v1/regional_hits | Find apps ranking high in one country but absent or far lower in the US. |
keyword_metrics | /v1/keywords | Rank keywords by opportunity, popularity or difficulty. |
get_app_intel | /v1/app_intel | Get one app’s ranks, estimate basis, 90-day rank history and keywords. |
aso_keyword_gap | /v1/aso_gap | List keywords competitors rank for that an app doesn’t. |
search_apps | /v1/search | Search the App Store live by keyword and country. |
get_app | /v1/app | Read a full live App Store listing. |
get_reviews | /v1/reviews | Read recent dated reviews with product themes. |
keyword_roadmap | /v1/market | Turn a keyword into a build roadmap from listings and reviews. |
Local HTTP
Prefer plain requests? Run the same ten operations as a small HTTP server on your own machine. Every path takes a JSON POST, and /openapi.json describes the inputs. It listens on 127.0.0.1 only.
Every response carries the snapshot date and coverage it answered from, the source URLs it read, and warnings about anything partial.
pnpm agent:serve --port 4319
curl http://127.0.0.1:4319/v1/discover \
-H 'Content-Type: application/json' \
-d '{"category":"Health & Fitness","minRevenue":10000,"sort":"revenue","limit":10}'What the numbers mean
Observed
Chart ranks, ratings, prices, release dates and search positions come straight from Apple’s public feeds, collected once a day in each country.
Estimated
Monthly revenue (developer net, USD) and downloads are modeled from chart position. Each comes with a low–high range, a confidence level and a basis that says how it was derived. Outside the US, estimates are scaled and marked low confidence.
Keyword scores
Popularity is a relative App Store autocomplete signal, not Apple Search Ads volume. Difficulty reflects how established the top 10 apps are. Opportunity weighs one against the other.
Full method: methodology. Detailed reference and the local tool contract: docs. Try the live Apple tools in the playground. Source on GitHub.