# App Review Intel - App Store & Google Play Reviews (`jongoose/app-review-intel-scraper`) Actor

Pull customer reviews from BOTH the Apple App Store and Google Play into one normalized schema: rating, title, body, author, date, app version, helpful votes, country. Resolve apps by id, URL, or search term. For product, CX and competitive review intelligence. No API key.

- **URL**: https://apify.com/jongoose/app-review-intel-scraper.md
- **Developed by:** [James Scott](https://apify.com/jongoose) (community)
- **Categories:** Lead generation, Marketing
- **Stats:** 2 total users, 1 monthly users, 60.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $1.00 / 1,000 results

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/platform/actors/running/actors-in-store#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.

In JavaScript/TypeScript projects, use official [JavaScript/TypeScript client](https://docs.apify.com/api/client/js/docs.md):

```bash
npm install apify-client
```

In Python projects, use official [Python client library](https://docs.apify.com/api/client/python/docs.md):

```bash
pip install apify-client
```

In shell scripts, use [Apify CLI](https://docs.apify.com/cli/docs.md):

````bash
# MacOS / Linux
curl -fsSL https://apify.com/install-cli.sh | bash
# Windows
irm https://apify.com/install-cli.ps1 | iex
```bash

In AI frameworks, you might use the [Apify MCP server](https://docs.apify.com/integrations/mcp.md).

If your project is in a different language, use 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 Review Intel - Apple App Store & Google Play Reviews

Pull **customer reviews from BOTH the Apple App Store and Google Play** into one clean,
**normalized** dataset - no account and no API key required. Point it at an app by store
id, by URL, or by a **search term**, and get every review from each store behind an
identical schema. Most review scrapers are single-store; this one unifies both, so you
can compare iOS vs. Android sentiment for the same app side by side.

Built for **product, CX, support and competitive-research teams** doing review
intelligence: release-regression tracking, feature requests, bug signal, star-rating
trends, and competitor teardowns.

### What you get (per review - identical fields on both stores)
| field | notes |
|-------|-------|
| `store` | `app_store` or `google_play` |
| `app_id` | App Store numeric id, or Google Play package name |
| `app_name` | Resolved app title |
| `review_id` | Stable per-review id |
| `rating` | Integer **1-5** |
| `title` | Review title (**Apple only** - Play reviews have no title, so `null`) |
| `body` | Review text |
| `author` | Reviewer display name |
| `review_date` | ISO-8601 timestamp |
| `app_version` | App version the review was written against (when present) |
| `helpful_count` | Apple: net "found helpful" votes; Google Play: thumbs-up count |
| `country` | Storefront the reviews were pulled from |

### Input
Give it **any one** of these ways to find an app (mix and match across stores):
- **Apple App Store ID** (e.g. `324684580`) or **App Store URL**
- **Google Play package ID** (e.g. `com.spotify.music`) or **Play URL**
- **Search term** (e.g. `spotify`) - resolves the top match on *each* store you did not
  pin explicitly, so one term can pull **both** stores' reviews for the same app.

Plus **country** (storefront, default `us`), **sort** (`recent` / `helpful` / `rating`),
and **max reviews per store** (default `200`).

#### Example input
```json
{
  "searchTerm": "spotify",
  "country": "us",
  "sort": "recent",
  "maxItems": 200,
  "proxyConfiguration": { "useApifyProxy": true }
}
````

Or pin each store precisely:

```json
{
  "appStoreId": "324684580",
  "playPackageId": "com.spotify.music",
  "maxItems": 500
}
```

#### Example output records

```json
{
  "store": "app_store",
  "app_id": "324684580",
  "app_name": "Spotify: Music and Podcasts",
  "review_id": "14283109848",
  "rating": 5,
  "title": "Spotify is my life support",
  "body": "Can’t live without",
  "author": "FlashD14",
  "review_date": "2026-07-09T11:40:40-07:00",
  "app_version": "9.1.62",
  "helpful_count": 0,
  "country": "us"
}
```

```json
{
  "store": "google_play",
  "app_id": "com.spotify.music",
  "app_name": "Spotify: Music and Podcasts",
  "review_id": "76a45471-1f9e-4604-821b-4c4949227d37",
  "rating": 5,
  "title": null,
  "body": "best ever!",
  "author": "John Campbell",
  "review_date": "2026-07-09T21:39:51+00:00",
  "app_version": "9.1.62.1601",
  "helpful_count": 0,
  "country": "us"
}
```

### How it works

- **Apple** reads the public **RSS customer-reviews JSON feed**
  (`.../rss/customerreviews/id=.../sortBy=.../page=.../json`) - ~50 reviews/page, up to
  10 pages (~500 reviews) per storefront. Apps resolve by name via the **iTunes Search
  API** and by id via **iTunes Lookup**.
- **Google Play** drives the Play web UI's internal **`batchexecute` RPC (`UsvDTd`)** - the
  same technique the open-source *google-play-scraper* uses - walking Play's own
  **pagination token** page by page (~100 reviews/page). Apps resolve by package id, by
  URL, or by Play search.
- Every field is read straight from these structured responses, so there are **no
  per-review detail requests** (fast + cheap), and both feeds work through Apify's
  **default datacenter proxy** - no pricey residential proxy needed.

#### Notes & limits

- The App Store's `mostHelpful` feed is empty for some apps; when the chosen sort returns
  nothing, the Actor automatically falls back to **most recent** so a run is never
  silently empty.
- The App Store RSS feed caps at ~**500 reviews** per storefront. To go deeper, run the
  same app across several **country** storefronts.
- Google Play reviews have **no title** (`title` is `null`); the App Store has no per-review
  thumbs-up, so `helpful_count` there is Apple's net helpful-vote sum.

Export as JSON, CSV, or Excel, or pull via the Apify API.

This is public review data provided for research; it is **not a consumer report** and must
**not** be used for any FCRA-covered purposes.

# Actor input Schema

## `appStoreId` (type: `string`):

Numeric App Store id of the app (e.g. 324684580 for Spotify). Leave blank to use an App Store URL or a Search term instead.

## `appStoreUrl` (type: `string`):

An apps.apple.com URL to pull the id from, e.g. https://apps.apple.com/us/app/spotify/id324684580. Used only if App Store ID is empty.

## `playPackageId` (type: `string`):

Android package name of the app (e.g. com.spotify.music). Leave blank to use a Play URL or a Search term instead.

## `playUrl` (type: `string`):

A play.google.com URL to pull the package id from, e.g. https://play.google.com/store/apps/details?id=com.spotify.music. Used only if the Play package ID is empty.

## `searchTerm` (type: `string`):

App name to search for. Resolves the top match on EACH store you have not pinned by id/URL - the App Store via the iTunes Search API and Google Play via Play search. Handy for pulling both stores' reviews for one app in a single run.

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

Two-letter storefront code the reviews are pulled from (App Store storefront + Play gl). Reviews and their language depend on this.

## `sort` (type: `string`):

Which reviews to pull first. 'recent' = newest, 'helpful' = most helpful / most relevant, 'rating' = highest rated (Google Play only; App Store falls back to newest).

## `maxItems` (type: `integer`):

Stop after collecting this many reviews from EACH store. Note the App Store RSS feed serves at most ~500 reviews (10 pages) per storefront.

## `proxyConfiguration` (type: `object`):

Both feeds work through Apify's default datacenter proxy - no residential proxy needed. Each request draws a fresh IP.

## Actor input object example

```json
{
  "appStoreId": "324684580",
  "playPackageId": "com.spotify.music",
  "searchTerm": "spotify",
  "country": "us",
  "sort": "recent",
  "maxItems": 200,
  "proxyConfiguration": {
    "useApifyProxy": true
  }
}
```

# 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 = {
    "searchTerm": "spotify"
};

// Run the Actor and wait for it to finish
const run = await client.actor("jongoose/app-review-intel-scraper").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 = { "searchTerm": "spotify" }

# Run the Actor and wait for it to finish
run = client.actor("jongoose/app-review-intel-scraper").call(run_input=run_input)

# Fetch and print Actor results from the run's dataset (if there are any)
print("💾 Check your data here: https://console.apify.com/storage/datasets/" + run["defaultDatasetId"])
for item in client.dataset(run["defaultDatasetId"]).iterate_items():
    print(item)

# 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/python/docs/quick-start

```

## CLI example

```bash
echo '{
  "searchTerm": "spotify"
}' |
apify call jongoose/app-review-intel-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "command": "npx",
            "args": [
                "mcp-remote",
                "https://mcp.apify.com/?tools=jongoose/app-review-intel-scraper",
                "--header",
                "Authorization: Bearer <YOUR_API_TOKEN>"
            ]
        }
    }
}

```

## OpenAPI specification

```json
{
    "openapi": "3.0.1",
    "info": {
        "title": "App Review Intel - App Store & Google Play Reviews",
        "description": "Pull customer reviews from BOTH the Apple App Store and Google Play into one normalized schema: rating, title, body, author, date, app version, helpful votes, country. Resolve apps by id, URL, or search term. For product, CX and competitive review intelligence. No API key.",
        "version": "0.1",
        "x-build-id": "t9NZPUUg2ke2Nfhgl"
    },
    "servers": [
        {
            "url": "https://api.apify.com/v2"
        }
    ],
    "paths": {
        "/acts/jongoose~app-review-intel-scraper/run-sync-get-dataset-items": {
            "post": {
                "operationId": "run-sync-get-dataset-items-jongoose-app-review-intel-scraper",
                "x-openai-isConsequential": false,
                "summary": "Executes an Actor, waits for its completion, and returns Actor's dataset items in response.",
                "tags": [
                    "Run Actor"
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "$ref": "#/components/schemas/inputSchema"
                            }
                        }
                    }
                },
                "parameters": [
                    {
                        "name": "token",
                        "in": "query",
                        "required": true,
                        "schema": {
                            "type": "string"
                        },
                        "description": "Enter your Apify token here"
                    }
                ],
                "responses": {
                    "200": {
                        "description": "OK"
                    }
                }
            }
        },
        "/acts/jongoose~app-review-intel-scraper/runs": {
            "post": {
                "operationId": "runs-sync-jongoose-app-review-intel-scraper",
                "x-openai-isConsequential": false,
                "summary": "Executes an Actor and returns information about the initiated run in response.",
                "tags": [
                    "Run Actor"
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "$ref": "#/components/schemas/inputSchema"
                            }
                        }
                    }
                },
                "parameters": [
                    {
                        "name": "token",
                        "in": "query",
                        "required": true,
                        "schema": {
                            "type": "string"
                        },
                        "description": "Enter your Apify token here"
                    }
                ],
                "responses": {
                    "200": {
                        "description": "OK",
                        "content": {
                            "application/json": {
                                "schema": {
                                    "$ref": "#/components/schemas/runsResponseSchema"
                                }
                            }
                        }
                    }
                }
            }
        },
        "/acts/jongoose~app-review-intel-scraper/run-sync": {
            "post": {
                "operationId": "run-sync-jongoose-app-review-intel-scraper",
                "x-openai-isConsequential": false,
                "summary": "Executes an Actor, waits for completion, and returns the OUTPUT from Key-value store in response.",
                "tags": [
                    "Run Actor"
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "$ref": "#/components/schemas/inputSchema"
                            }
                        }
                    }
                },
                "parameters": [
                    {
                        "name": "token",
                        "in": "query",
                        "required": true,
                        "schema": {
                            "type": "string"
                        },
                        "description": "Enter your Apify token here"
                    }
                ],
                "responses": {
                    "200": {
                        "description": "OK"
                    }
                }
            }
        }
    },
    "components": {
        "schemas": {
            "inputSchema": {
                "type": "object",
                "properties": {
                    "appStoreId": {
                        "title": "Apple App Store ID",
                        "type": "string",
                        "description": "Numeric App Store id of the app (e.g. 324684580 for Spotify). Leave blank to use an App Store URL or a Search term instead."
                    },
                    "appStoreUrl": {
                        "title": "Apple App Store URL",
                        "type": "string",
                        "description": "An apps.apple.com URL to pull the id from, e.g. https://apps.apple.com/us/app/spotify/id324684580. Used only if App Store ID is empty."
                    },
                    "playPackageId": {
                        "title": "Google Play package ID",
                        "type": "string",
                        "description": "Android package name of the app (e.g. com.spotify.music). Leave blank to use a Play URL or a Search term instead."
                    },
                    "playUrl": {
                        "title": "Google Play URL",
                        "type": "string",
                        "description": "A play.google.com URL to pull the package id from, e.g. https://play.google.com/store/apps/details?id=com.spotify.music. Used only if the Play package ID is empty."
                    },
                    "searchTerm": {
                        "title": "Search term (resolve app by name)",
                        "type": "string",
                        "description": "App name to search for. Resolves the top match on EACH store you have not pinned by id/URL - the App Store via the iTunes Search API and Google Play via Play search. Handy for pulling both stores' reviews for one app in a single run."
                    },
                    "country": {
                        "title": "Country / storefront",
                        "type": "string",
                        "description": "Two-letter storefront code the reviews are pulled from (App Store storefront + Play gl). Reviews and their language depend on this.",
                        "default": "us"
                    },
                    "sort": {
                        "title": "Sort order",
                        "enum": [
                            "recent",
                            "helpful",
                            "rating"
                        ],
                        "type": "string",
                        "description": "Which reviews to pull first. 'recent' = newest, 'helpful' = most helpful / most relevant, 'rating' = highest rated (Google Play only; App Store falls back to newest).",
                        "default": "recent"
                    },
                    "maxItems": {
                        "title": "Max reviews per store",
                        "minimum": 1,
                        "type": "integer",
                        "description": "Stop after collecting this many reviews from EACH store. Note the App Store RSS feed serves at most ~500 reviews (10 pages) per storefront.",
                        "default": 200
                    },
                    "proxyConfiguration": {
                        "title": "Proxy",
                        "type": "object",
                        "description": "Both feeds work through Apify's default datacenter proxy - no residential proxy needed. Each request draws a fresh IP.",
                        "default": {
                            "useApifyProxy": true
                        }
                    }
                }
            },
            "runsResponseSchema": {
                "type": "object",
                "properties": {
                    "data": {
                        "type": "object",
                        "properties": {
                            "id": {
                                "type": "string"
                            },
                            "actId": {
                                "type": "string"
                            },
                            "userId": {
                                "type": "string"
                            },
                            "startedAt": {
                                "type": "string",
                                "format": "date-time",
                                "example": "2025-01-08T00:00:00.000Z"
                            },
                            "finishedAt": {
                                "type": "string",
                                "format": "date-time",
                                "example": "2025-01-08T00:00:00.000Z"
                            },
                            "status": {
                                "type": "string",
                                "example": "READY"
                            },
                            "meta": {
                                "type": "object",
                                "properties": {
                                    "origin": {
                                        "type": "string",
                                        "example": "API"
                                    },
                                    "userAgent": {
                                        "type": "string"
                                    }
                                }
                            },
                            "stats": {
                                "type": "object",
                                "properties": {
                                    "inputBodyLen": {
                                        "type": "integer",
                                        "example": 2000
                                    },
                                    "rebootCount": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "restartCount": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "resurrectCount": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "computeUnits": {
                                        "type": "integer",
                                        "example": 0
                                    }
                                }
                            },
                            "options": {
                                "type": "object",
                                "properties": {
                                    "build": {
                                        "type": "string",
                                        "example": "latest"
                                    },
                                    "timeoutSecs": {
                                        "type": "integer",
                                        "example": 300
                                    },
                                    "memoryMbytes": {
                                        "type": "integer",
                                        "example": 1024
                                    },
                                    "diskMbytes": {
                                        "type": "integer",
                                        "example": 2048
                                    }
                                }
                            },
                            "buildId": {
                                "type": "string"
                            },
                            "defaultKeyValueStoreId": {
                                "type": "string"
                            },
                            "defaultDatasetId": {
                                "type": "string"
                            },
                            "defaultRequestQueueId": {
                                "type": "string"
                            },
                            "buildNumber": {
                                "type": "string",
                                "example": "1.0.0"
                            },
                            "containerUrl": {
                                "type": "string"
                            },
                            "usage": {
                                "type": "object",
                                "properties": {
                                    "ACTOR_COMPUTE_UNITS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATASET_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATASET_WRITES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "KEY_VALUE_STORE_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "KEY_VALUE_STORE_WRITES": {
                                        "type": "integer",
                                        "example": 1
                                    },
                                    "KEY_VALUE_STORE_LISTS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "REQUEST_QUEUE_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "REQUEST_QUEUE_WRITES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATA_TRANSFER_INTERNAL_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATA_TRANSFER_EXTERNAL_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "PROXY_SERPS": {
                                        "type": "integer",
                                        "example": 0
                                    }
                                }
                            },
                            "usageTotalUsd": {
                                "type": "number",
                                "example": 0.00005
                            },
                            "usageUsd": {
                                "type": "object",
                                "properties": {
                                    "ACTOR_COMPUTE_UNITS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATASET_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATASET_WRITES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "KEY_VALUE_STORE_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "KEY_VALUE_STORE_WRITES": {
                                        "type": "number",
                                        "example": 0.00005
                                    },
                                    "KEY_VALUE_STORE_LISTS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "REQUEST_QUEUE_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "REQUEST_QUEUE_WRITES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATA_TRANSFER_INTERNAL_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATA_TRANSFER_EXTERNAL_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "PROXY_SERPS": {
                                        "type": "integer",
                                        "example": 0
                                    }
                                }
                            }
                        }
                    }
                }
            }
        }
    }
}
```
