# App Store Data API - Search, Sales, Ratings, Reviews (`nabeelbaghoor/app-store-data-api`) Actor

Search the App Store, Google Play, Amazon Appstore and Microsoft Store by app name or developer, look up any app by its store id or listing URL, and read sales, rating history, category ranks and reviews for the apps your account has connected. Bring your own key.

- **URL**: https://apify.com/nabeelbaghoor/app-store-data-api.md
- **Developed by:** [Nabeel Hassan](https://apify.com/nabeelbaghoor) (community)
- **Categories:** Business, Developer tools, Lead generation
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $10.00 / 1,000 app returneds

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.

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

## What's an Apify Actor?

Actors are web data automations that power AI and operations. They run on the Apify platform to scrape websites, process data, connect APIs, and automate workflows.
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.
Actors are written with capital "A".

## 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.
The best way to integrate Actors is as follows.

- **AI agents and MCP clients** — the [Apify MCP server](https://docs.apify.com/integrations/mcp.md) at `https://mcp.apify.com` (remote, streamable HTTP, OAuth on first use).
- **Agentic workflows and local Actor development** — [Agent Skills](https://apify.com/.well-known/agent-skills/index.json) with the [Apify CLI](https://docs.apify.com/cli/docs.md): `npm install -g apify-cli`, then `apify login`.
- **JavaScript/TypeScript projects** — the official [JS/TS client](https://docs.apify.com/api/client/js/docs.md): `npm install apify-client`.
- **Python projects** — the official [Python client](https://docs.apify.com/api/client/python/docs.md): `pip install apify-client`.
- **Any other language** — the [REST API](https://docs.apify.com/api/v2.md).

For usage examples, see the [API](#api) section below.

For more details, see Apify documentation as [Markdown index](https://docs.apify.com/llms.txt) and [Markdown full-text](https://docs.apify.com/llms-full.txt).

# README

## App Store Data API - Search, Sales, Ratings, Reviews

Search four app stores by name or by developer, look up any app by its listing URL, and pull your own sales, ratings, ranks and reviews as rows you can put in a spreadsheet.

### What it does

- **Searches four stores at once.** Apple App Store, Google Play, Amazon Appstore and Microsoft Store, by app name or, with an `@developer=` term, by who publishes it.
- **Takes store listing URLs.** Paste an App Store or Google Play URL and the identifier is read out of it, so you do not have to know that 284882215 is Facebook.
- **Flattens nested reports into rows.** A report grouped by app, country and date comes back from the provider nested three levels deep. This actor walks it and writes one flat row per cell, carrying the app, country, store and date down into each one.
- **Splits star ratings into columns.** A ratings breakdown arrives as an array of five numbers; rows carry one star, two star, three star, four star and five star as their own fields, so they sort and filter.
- **Reviews with everything attached.** Star rating, title, body, author, app version, country and language, paged until the date range is exhausted.
- **Says when a report is empty and why.** Report and review routes describe the apps your account has connected, not any app in the store. An empty answer is reported as that fact rather than left looking like a broken run.
- **Keeps the misses.** A term that matches nothing, or an identifier the stores have no record of, still produces a row saying so, and it is not charged for.

### Input

#### Search the stores by name

```json
{
  "mode": "search",
  "searchTerms": ["meditation", "@developer=Calm"],
  "store": "apple",
  "maxResults": 200
}
```

#### Look up apps you already have

```json
{
  "mode": "products",
  "store": "apple",
  "products": ["284882215", "https://apps.apple.com/us/app/nfl/id389781154"]
}
```

#### Daily sales for your connected apps

```json
{
  "mode": "sales",
  "startDate": "2026-08-01",
  "endDate": "2026-08-31",
  "granularity": "daily",
  "groupBy": ["country"],
  "countries": ["US", "GB"],
  "maxResults": 1000
}
```

#### Reviews

```json
{
  "mode": "reviews",
  "startDate": "2026-08-01",
  "endDate": "2026-08-31",
  "language": "en",
  "maxResults": 500
}
```

### Example output

An app row and a sales report row.

```json
{
  "recordType": "product",
  "requested": "meditation",
  "productId": "40994847",
  "name": "Calm",
  "developer": "Calm.com, Inc.",
  "store": "apple",
  "storeId": "apple",
  "vendorIdentifier": "571800810",
  "refNo": "571800810",
  "type": "app",
  "devices": ["iphone", "ipad"],
  "releaseDate": "2012-11-08",
  "version": "6.42",
  "price": 0,
  "currency": "USD",
  "found": true
}
```

```json
{
  "recordType": "sales",
  "productId": "40994847",
  "country": "US",
  "date": "2026-08-14",
  "downloads": 18422,
  "updates": 91043,
  "revenue": 41208.55,
  "returns": -12,
  "found": true
}
```

### Bring your own key

This actor calls an app store data API with **your own account's personal access token**. Generate one against an API client in your account settings, then paste it into the personal access token field or set it as the `DATA_API_KEY` environment secret. Some accounts also need the client key, which has its own field. Neither is ever written to the dataset or the log.

Without a token the run ends cleanly and tells you what to add, rather than failing.

### Pricing

Pay per result, platform usage included.

| Event | Price |
| --- | --- |
| App returned | $0.01 |
| Report row returned | $0.006 |
| Review returned | $0.004 |

Terms that match nothing, identifiers the stores have no record of, and reports that come back empty are never charged.

### FAQ

#### What app stores does this API cover?

The Apple App Store, Google Play, the Amazon Appstore and the Microsoft Store. Search and product lookup work across all of them; set the store field to narrow to one.

#### Can I search the App Store by developer name?

Yes. Prefix a search term with `@developer=`, for example `@developer=Calm`, and the search matches the developer rather than the app name.

#### What is the difference between search and the sales report?

Search and product lookup describe any app in the stores, so they work for competitor research. The sales, ratings, ranks and reviews reports describe the apps your own account has connected, so they answer with your data and come back empty for apps that are not linked to your account.

#### How do I get daily downloads and revenue for my own apps?

Use `mode: "sales"` with a start and end date and `granularity: "daily"`. Add `groupBy: ["country"]` to break each day down by country. Each cell becomes one flat row.

#### Why is my report empty?

Report routes only cover connected products. An empty report means either no connected app had activity in the range you asked for, or the apps you listed are not linked to your account. The run says so in the log and stores a row noting it, rather than failing.

#### What identifiers can I use?

An Apple store id such as `284882215`, a Google Play package name, one of the provider's own product ids, or a store listing URL containing any of those. URLs are parsed for you.

#### How are star ratings returned?

Both ways. Each report row carries the rating average and total, and when the provider sends a five-number breakdown, the row also carries `oneStar` through `fiveStar` as separate numeric fields.

#### Do I need my own API key?

Yes. This actor is bring-your-own-key: it calls the provider with your account's personal access token, so you keep your own plan, scopes and terms. There is no shared or bundled key.

#### Does this need an OAuth flow?

No. A personal access token is issued by hand from your account and passed as a bearer token, so nothing here implements OAuth and nothing here sees your password.

#### How is the price calculated?

Per row stored. App rows are $0.01, report rows are $0.006 and reviews are $0.004. Rows saying something was not found cost nothing.

### Keyword map

app store data API, google play data API, app search API, app store sales report API, app downloads and revenue API, app ratings API, app reviews API, app store ranks API, mobile app analytics API, app store connect alternative, app store listing lookup, amazon appstore data, microsoft store app data, app developer search

# Actor input Schema

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

A run answers one question. Search and products describe any app in the stores. Sales, ratings, ranks and reviews describe the products your own account has connected, and come back empty for apps that are not linked to it. Fields belonging to another mode are ignored rather than causing an error.

## `apiKey` (type: `string`):

Your own account's personal access token for this provider, issued from an API client in your account settings. Bring your own key: nothing is shared between runs and the token is never written to the dataset or the log.

## `clientKey` (type: `string`):

The API client key, for accounts whose setup requires it alongside the token. Most personal access tokens work without it, so leave it empty unless the provider told you otherwise.

## `searchTerms` (type: `array`):

Terms to search the stores for, one per line, matched against app names. Prefix a term with @developer= to search by developer instead, for example @developer=angry.

## `products` (type: `array`):

Apps to read, one per line. A store id such as 284882215, a Google Play package name, one of the provider's own product ids, or a store listing URL that carries one. Also narrows a sales, ratings, ranks or reviews report to these apps.

## `store` (type: `string`):

Which store an app identifier belongs to, used when looking an app up by its store id and to narrow a search. Leave empty to look up by the provider's own product id and to search every store.

## `startDate` (type: `string`):

First day to cover, as YYYY-MM-DD. Used by the sales, ratings, ranks and reviews modes. Defaults to 30 days before the end date.

## `endDate` (type: `string`):

Last day to cover, as YYYY-MM-DD. Used by the sales, ratings, ranks and reviews modes. Defaults to yesterday.

## `granularity` (type: `string`):

How a report is bucketed in time. Daily gives one row per app per day, which is the most detail and the most rows.

## `groupBy` (type: `array`):

Extra breakdowns for a report. Product and date are always included, because a row without them is a total rather than a row. Adding country or store multiplies the number of rows.

## `countries` (type: `array`):

Two letter country codes to limit a report or a review run to, one per line, such as US or GB. Leave empty for every country.

## `language` (type: `string`):

Translate or filter reviews to one language, as a two letter code such as en. Leave empty to take reviews in whatever language they were written in.

## `maxResults` (type: `integer`):

The most rows this run may store, and so the most it can charge for. A daily sales report broken down by country produces a row per app, per country, per day, so this is the cap that keeps a run predictable.

## `requestsPerMinute` (type: `integer`):

How fast this run calls the provider. Lower it if your plan is rate limited more tightly than the default.

## `baseUrl` (type: `string`):

Overrides the API host. Only needed if the provider has given your account a different endpoint.

## Actor input object example

```json
{
  "mode": "search",
  "searchTerms": [
    "meditation"
  ],
  "store": "",
  "granularity": "daily",
  "groupBy": [],
  "maxResults": 100,
  "requestsPerMinute": 120
}
```

# Actor output Schema

## `records` (type: `string`):

One row per record, alongside the app, country and date that produced it.

# 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 = {
    "searchTerms": [
        "meditation"
    ]
};

// Run the Actor and wait for it to finish
const run = await client.actor("nabeelbaghoor/app-store-data-api").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 = { "searchTerms": ["meditation"] }

# Run the Actor and wait for it to finish
run = client.actor("nabeelbaghoor/app-store-data-api").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 '{
  "searchTerms": [
    "meditation"
  ]
}' |
apify call nabeelbaghoor/app-store-data-api --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,nabeelbaghoor/app-store-data-api"
        }
    }
}

```

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/Rn9EiXBXXP9gqrNQ1/builds/XEoXAYxfVaKdaKT7u/openapi.json
