# ASO Keyword Rankings API - App Store Keyword Data (`nabeelbaghoor/aso-keyword-rankings-api`) Actor

App store optimization data as rows: keyword volume, difficulty and reach, where an app ranks for each keyword, the live App Store and Google Play search results for a keyword, suggested keywords, top charts, full store listings and reviews, across 100+ countries. Bring your own key.

- **URL**: https://apify.com/nabeelbaghoor/aso-keyword-rankings-api.md
- **Developed by:** [Nabeel Hassan](https://apify.com/nabeelbaghoor) (community)
- **Categories:** SEO tools, Business, Developer tools
- **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 listing 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

## ASO Keyword Rankings API - App Store Keyword Data

Everything app store optimization runs on, as rows: what a keyword is worth, how hard it is, who ranks for it today, and what the store actually returns when somebody types it.

### What it does

- **Keyword metrics that mean something.** Search volume, maximum volume, difficulty, maximum reach, total results and whether the term is a brand, per country and per device.
- **Live store search results.** The organic App Store or Google Play result for a keyword, as one row per app in rank order, read at the moment you run it.
- **Keyword rankings for your apps.** Where each app ranks on the keywords it is tracked for, with the volume and difficulty of each keyword on the same row.
- **Keyword suggestions.** The keywords the provider recommends for an app, with volume and difficulty attached, so a shortlist is a filter rather than a brainstorm.
- **Top charts.** Top free, top paid or top grossing for any store category, up to 500 apps, as ranked rows.
- **Full store listings.** Title, subtitle, description, developer, categories, price, size, release date, current version, release notes, screenshots, rating, and the provider's app and game DNA classification.
- **Reviews with ratings.** Store reviews over a date range, with rating, title, body, author and app version.
- **Never spends your credits behind your back.** Downloads and revenues cost 500 provider credits per app against 10 for ratings and app power, so metrics are an explicit choice. Leave the field empty and a metrics run reads only the cheap ones.
- **Reports what each run cost.** The provider returns the credit cost of every request; the run totals it and puts it in the final status message.
- **Batches to the provider's ceiling.** Five app identifiers per request is the provider's limit, so longer lists are split for you and spend as few requests as possible.
- **Keeps the misses.** An app or keyword the provider has no data for still produces a row saying so, and it is not charged for.

### Input

#### What is a keyword worth?

```json
{
  "mode": "keywordMetrics",
  "keywords": ["meditation", "sleep sounds", "breathing exercises"],
  "country": "us",
  "device": "iphone"
}
```

#### Who ranks for a keyword right now?

```json
{
  "mode": "keywordSearch",
  "keywords": ["meditation"],
  "country": "us",
  "device": "android",
  "maxResults": 100
}
```

#### Where do my apps rank?

```json
{
  "mode": "keywordRankings",
  "apps": ["284882215", "com.calm.android"],
  "country": "us",
  "device": "iphone",
  "maxResults": 500
}
```

#### The top free chart for a category

```json
{
  "mode": "topCharts",
  "category": "6005",
  "chartType": "free",
  "country": "us",
  "device": "iphone",
  "maxResults": 500
}
```

#### Downloads and revenue history, deliberately

```json
{
  "mode": "metrics",
  "apps": ["284882215"],
  "metrics": ["downloads", "revenues"],
  "history": true,
  "startDate": "2026-08-01",
  "endDate": "2026-08-31"
}
```

### Example output

A keyword row and a live search row.

```json
{
  "recordType": "keyword",
  "keyword": "meditation",
  "country": "us",
  "device": "iphone",
  "date": "2026-09-02",
  "volume": 62,
  "maxVolume": 100,
  "difficulty": 48,
  "maxReach": 91,
  "totalResults": 1840,
  "isBrand": false,
  "found": true
}
```

```json
{
  "recordType": "searchResult",
  "appId": "571800810",
  "keyword": "meditation",
  "country": "us",
  "device": "iphone",
  "rank": 1,
  "found": true
}
```

### Bring your own key

This actor calls an app store optimization API with **your own account's API token**, copied from the API dashboard in your provider account. Paste it into the API key field, or set it as the `DATA_API_KEY` environment secret. It is never 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 listing returned | $0.01 |
| Keyword or ranking row returned | $0.006 |
| Review returned | $0.004 |

Rows for apps and keywords the provider has no data for, and requests it refused, are never charged.

### FAQ

#### What is an ASO API?

An app store optimization API returns the data behind app store search: how much a keyword is searched, how hard it is to rank for, which apps currently rank for it, and how a given app's listing and rankings are changing. It is the App Store and Google Play equivalent of a keyword research tool for web SEO.

#### What keyword metrics does it return?

Search volume, maximum volume, difficulty, maximum reach, total results in the store for that term, and whether the term is a brand. All of them are per country and per device, because store search is per country.

#### Can I see the live App Store search results for a keyword?

Yes. Use `mode: "keywordSearch"` with one or more keywords. Each run reads the store's organic result at that moment and returns one row per app in rank order.

#### Does it work for Google Play as well as the App Store?

Yes. Set `device` to `android` for Google Play, or `iphone` or `ipad` for the App Store. Store categories differ between the two: the App Store uses numbers such as `6005`, Google Play uses names such as `GAME_ACTION`.

#### How many countries are covered?

The provider covers over 100 countries and more than five million apps. Set the two-letter country code in the country field; the data returned is that country's store, not a filtered view of a global one.

#### Why are downloads and revenue not included by default?

Because they are expensive. On this provider's credit model, downloads and revenues cost 500 credits per app, while ratings, daily ratings and app power cost 10. Nothing costly is added to a request on your behalf, so a metrics run with the field left empty reads only the cheap metrics.

#### How do I get keyword suggestions for my app?

Use `mode: "suggestions"` with your app identifiers. Each suggested keyword comes back with its volume and difficulty, so you can sort a shortlist instead of guessing.

#### What app identifiers does it take?

An App Store numeric id, a Google Play package name, or a store listing URL containing either. URLs are parsed for you. Five apps go into each provider request, and longer lists are batched automatically.

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

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

#### How is the price calculated?

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

### Keyword map

ASO API, app store optimization API, app keyword ranking API, keyword volume difficulty API, app store keyword research, google play keyword API, app store search results API, top charts API, keyword suggestions API, app store listing API, app reviews API, mobile app SEO, app store rank tracking, ASO keyword tool API

# Actor input Schema

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

A run answers one question. Some modes read about apps and some read about keywords, so the fields belonging to another mode are ignored rather than causing an error.

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

Your own account's API token for this provider, copied from its API dashboard. Bring your own key: nothing is shared between runs and the token is never written to the dataset or the log.

## `apps` (type: `array`):

Apps to read, one per line. An App Store numeric id such as 284882215, a Google Play package name such as com.facebook.katana, or a store listing URL that carries one. The provider accepts five apps per request, so longer lists are batched for you.

## `keywords` (type: `array`):

Keywords to read, one per line, written as you would type them into the store search box. Used by the keyword metrics and keyword search modes.

## `country` (type: `string`):

Two letter country code for the store to read, such as us, gb or de. Store data is per country, so this changes the answer rather than filtering it.

## `device` (type: `string`):

Which store and form factor to read. iPhone and iPad read the App Store, and android reads Google Play.

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

Two letter language code for the listing text, such as en. Leave empty for the country's default language.

## `metrics` (type: `array`):

Which metrics the metrics mode asks for. Downloads and revenues cost 500 provider credits per app, while ratings, daily ratings and app power cost 10, so nothing expensive is ever added on your behalf. Leaving this empty reads ratings and app power only.

## `history` (type: `boolean`):

Read the historical series over the date range rather than the most recent value. Applies to the metrics and keyword metrics modes.

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

First day to cover, as YYYY-MM-DD. Used when reading history, and by the reviews mode. Defaults to 30 days before the end date.

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

Last day to cover, as YYYY-MM-DD. Used when reading history, and by the reviews mode. Defaults to yesterday.

## `category` (type: `string`):

The category to chart in top charts mode. A number such as 6005 on the App Store, or a name such as GAME\_ACTION on Google Play. Passing one store's vocabulary to the other returns nothing rather than an error.

## `chartType` (type: `string`):

Which chart to read in top charts mode. The top 500 apps are available for each.

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

The most rows this run may store, and so the most it can charge for. A top chart is up to 500 rows and a keyword ranking run is one row per keyword per app, so this is the cap that keeps a run predictable.

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

How fast this run calls the provider. The documented ceiling is 60 requests per 10 seconds; lower this if your plan is tighter.

## `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": "metadata",
  "apps": [
    "284882215"
  ],
  "country": "us",
  "device": "iphone",
  "metrics": [],
  "history": false,
  "chartType": "free",
  "maxResults": 100,
  "requestsPerMinute": 300
}
```

# Actor output Schema

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

One row per record, alongside the app, keyword, country and device 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 = {
    "apps": [
        "284882215"
    ]
};

// Run the Actor and wait for it to finish
const run = await client.actor("nabeelbaghoor/aso-keyword-rankings-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 = { "apps": ["284882215"] }

# Run the Actor and wait for it to finish
run = client.actor("nabeelbaghoor/aso-keyword-rankings-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 '{
  "apps": [
    "284882215"
  ]
}' |
apify call nabeelbaghoor/aso-keyword-rankings-api --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,nabeelbaghoor/aso-keyword-rankings-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/aZ8DZjrO3VXlYkChH/builds/lbXJEnjMAWAVZZQI0/openapi.json
