If you build or market an Android app, the reviews of your competitors are some of the most useful free research you can get. Users write down exactly which feature is missing, which update broke something, and which price change made them leave. The problem is getting those reviews out of the Play Store and into a spreadsheet where you can actually work with them.

This guide shows one way to do that without an API key and without writing code. There is also an optional Python section at the end.

Disclosure: I built and maintain this Actor. The tool used below is my own Google Play Reviews Scraper on Apify. I'll try to be clear about what it can and can't do.

Why the Play Console doesn't solve this

Google does give developers access to reviews, but only for apps you own. The Play Console shows reviews of your published apps, and the Google Play Developer API lets you read and reply to them, but the API only returns reviews created or edited in roughly the last week. Neither shows you anything about apps published by someone else.

So for competitor research you have three options: read the store page by hand and copy-paste, write and maintain your own scraper, or use a ready-made one.

What you can use the data for

A few concrete things people do with exported reviews:

  • Competitor research. Pull the newest 1,000 reviews of three competing apps and see what each one is praised and criticized for.
  • Finding feature requests and bugs. Filter to 1-star and 2-star reviews. These are where users describe broken flows and missing features in detail.
  • Tracking reaction to releases. Every review carries the app version it was written on, so you can group complaints by version and see whether a release made things better or worse.

Step by step in Apify Console

  1. Open the Actor page and click Try for free (you need an Apify account).
  2. In What to scrape, keep Reviews of apps.
  3. In Apps, paste one or more Google Play links or app ids. The app id is the part after id= in the link: for https://play.google.com/store/apps/details?id=com.duolingo it is com.duolingo. Either format works.
  4. Set Max results (total reviews for the run, default 100). If you scrape several apps, Max reviews per app stops one big app from using up the whole budget.
  5. Choose Sort reviews by: Newest (good for monitoring), Most relevant (the order Google Play shows visitors) or Highest rating first.
  6. Optionally set Star rating to keep only 1-star reviews, or any other single rating.
  7. Set Language (for example en, de, pt-BR) and Country (two-letter code like us, gb, jp). Defaults are en and us.
  8. Click Start. When the run finishes, open the Output tab and export as JSON, CSV or Excel.

No Google account, login or proxy is needed.

The JSON input for the test run I did for this article looked like this:

{ "mode": "reviews", "appIds": ["https://play.google.com/store/apps/details?id=com.duolingo"], "sort": "newest", "rating": "1", "language": "en", "country": "us", "maxItems": 20 } 

It finished in about 4 seconds and saved 20 reviews.

What the output looks like

Here are two of those 20 reviews. I only redacted the user names and avatar links:

[ { "type": "review", "reviewId": "f3eaabac-31ec-4558-ab1d-610077774468", "appId": "com.duolingo", "appName": "Duolingo: Learn Languages", "userName": "(redacted)", "userImage": "https://play-lh.googleusercontent.com/...", "rating": 1, "text": "This app is very frustrating due to the endless screens you have to click through, even when you have a paid subscription. I really wish you could turn off all of these random screens for gems, chests, invites, progress, friend streaks, puzzles, and even more expensive subscriptions. It would be 5 stars if you could choose which features have popups instead of being forced to wade through the endless popups.", "thumbsUp": 233, "appVersion": "6.102.4", "postedAt": "2026-10-26T16:26:11Z", "developerReplyText": null, "developerReplyAt": null, "language": "en", "country": "us", "url": "https://play.google.com/store/apps/details?id=com.duolingo&reviewId=f3eaabac-31ec-4558-ab1d-610077774468", "scrapedAt": "2026-10-27T21:20:27Z" }, { "type": "review", "reviewId": "4aa247ff-0567-49f5-a2bf-3cf62bb2dd20", "appId": "com.duolingo", "appName": "Duolingo: Learn Languages", "userName": "(redacted)", "userImage": "https://play-lh.googleusercontent.com/...", "rating": 1, "text": "You need to focus on better lessons and fixing all of these bugs! it's so bad! Instead they're pushing usless AI and tying them to higher priced subscriptions. They've lost their way and are actively making it a worse app. Removing a star because your speaking exercises don't even load anymore.", "thumbsUp": 0, "appVersion": "6.102.4", "postedAt": "2026-10-26T19:20:43Z", "developerReplyText": null, "developerReplyAt": null, "language": "en", "country": "us", "url": "https://play.google.com/store/apps/details?id=com.duolingo&reviewId=4aa247ff-0567-49f5-a2bf-3cf62bb2dd20", "scrapedAt": "2026-10-27T21:20:27Z" } ] 

thumbsUp is the number of other users who marked the review as helpful, which makes it a good way to rank complaints. When the developer has answered, developerReplyText and developerReplyAt are filled in.

Doing the same from Python

If you'd rather script it, the official apify-client package works (pip install apify-client pandas). You need your Apify API token from the Console settings.

from apify_client import ApifyClient import pandas as pd client = ApifyClient("YOUR_APIFY_TOKEN") run = client.actor("pipiagent/google-play-reviews-scraper").call(run_input={ "mode": "reviews", "appIds": ["com.duolingo"], "sort": "newest", "rating": "1", "language": "en", "country": "us", "maxItems": 1000, }) items = list(client.dataset(run["defaultDatasetId"]).iterate_items()) df = pd.DataFrame(items) df.to_csv("duolingo_1star.csv", index=False) 

Now a quick look at what the 1-star reviews are about. This counts how many reviews mention each keyword, and how many helpful votes those reviews collected:

keywords = ["subscription", "ads", "bug", "crash", "refund", "streak", "ai"] text = df["text"].fillna("").str.lower() summary = pd.DataFrame({ kw: { "reviews": text.str.contains(rf"\b{kw}\b").sum(), "helpful_votes": df.loc[text.str.contains(rf"\b{kw}\b"), "thumbsUp"].sum(), } for kw in keywords }).T.sort_values("reviews", ascending=False) print(summary) 

To look at reaction to a release, group by version instead: df.groupby("appVersion").size(). Keep in mind that appVersion is empty for some reviews.

What it costs

The Actor is pay per result: $0.20 per 1,000 reviews, with no start fee or monthly rental. Some examples:

  • The 20-review test above: $0.004
  • 1,000 newest 1-star reviews of one app: $0.20
  • 2,000 reviews each for 5 competitor apps (10,000 reviews): $2.00

You can set a maximum charge per run in the run options, and the run stops when it reaches it.

Limitations

Some things to know before you rely on it:

  • One language per run. Google Play returns reviews for the language you choose. For several languages, start one run per language. The filter is Google's, not exact: in my 20-review English test, one review was written in French.
  • Only reviews with text. Most users leave stars without writing anything. Those ratings can't be collected, so the number of reviews is much smaller than the rating count shown on the store page.
  • appVersion is sometimes empty. Some reviews have no version (1 of 20 in my test), so version-based analysis covers most reviews, not all of them.
  • The date is the last edit. If a user edits a review after the developer replied, the reply can be older than the review.
  • Personal data. Results include public user names and avatars. If you store or process them, make sure you have a legitimate reason under GDPR or similar laws, or drop those columns.
  • Tested scale. Runs of up to 20,000 reviews were tested on Apify. Much larger runs should work but haven't been tested there.

The Actor also has two other modes, app details (rating breakdown, installs, price, version) and keyword search, which are useful for building a competitor list before you pull reviews.

If you try it and something is broken or missing, the Issues tab on the Actor page is the best place to report it.