앱 스토어 및 Google Play 리뷰 스크래핑: 엔드포인트, 제한, 지역
앱 리뷰는 가장 저렴한 제품 연구 수단입니다 - 페이지네이션 제한, 토큰 벽, 국가별 스토어프론트를 넘어설 수 있다면 말입니다. 여기에 전체 지도가 있습니다.
앱 리뷰는 가장 저렴한 고객 연구 수단입니다: 필터링되지 않은 기능 요청, 특정 버전에 연결된 버그 리포트, 카테고리 내 모든 경쟁자에 대한 지속적인 감정 읽기. 문제는 접근성입니다. 두 스토어 모두 페이지에 몇 개의 리뷰만 표시하고 나머지는 피드, 토큰 및 국가별 스토어프론트 뒤에 숨깁니다. 이 가이드는 앱 스토어 및 Google Play 리뷰 스크래핑 방법을 안내합니다 - 실제 엔드포인트, 아무도 경고하지 않는 페이지네이션 제한, 그리고 몇 백 개의 행을 넘어 파이프라인이 살아남을 수 있는지 결정하는 지역 및 속도 제한 현실.
Apple, 쉬운 방법: RSS 피드
Apple은 토큰이 필요 없는 고객 리뷰의 공개 JSON 피드를 제공합니다. 이는 시작하기에 가장 빠른 방법이며, 깨끗하고 구조화된 기록 - 평점, 제목, 본문, 작성자, 앱 버전을 반환합니다. 제한은 명확한 상한선입니다: 피드는 대략 50개의 리뷰가 있는 최대 10페이지를 제공하므로, 앱당 스토어프론트당 약 500개의 리뷰가 최신 리뷰에 치우쳐 제공됩니다. 신선한 피드백을 모니터링하기에는 종종 충분하지만, 전체 기록을 위해서는 그렇지 않습니다.
import requests
def apple_rss_reviews(app_id, country="us", pages=10):
out = []
for page in range(1, pages + 1): # feed caps out around page 10
url = (f"https://itunes.apple.com/{country}/rss/customerreviews/"
f"page={page}/id={app_id}/sortby=mostrecent/json")
# route through a residential exit in the target storefront's country
proxy = f"http://USER-country-{country}:PASS@gate.quantumproxies.io:8000"
r = requests.get(url, proxies={"https": proxy}, timeout=20)
entries = r.json().get("feed", {}).get("entry", [])
for e in entries[1:]: # first entry is app metadata, skip it
out.append({
"rating": e["im:rating"]["label"],
"version": e["im:version"]["label"],
"title": e["title"]["label"],
"text": e["content"]["label"],
"author": e["author"]["name"]["label"],
})
if len(entries) <= 1:
break
return out
Apple, 깊이 있는 방법: 앱 스토어 API 및 그 토큰
500개를 넘어서기 위해서는 앱 스토어 웹 페이지가 호출하는 동일한 엔드포인트(AMP / MZStore API)를 사용합니다. 이는 더 풍부한 기록 - 리뷰 ID, 편집 플래그, 개발자 응답 - 을 반환하지만, 먼저 앱의 공개 웹 페이지에서 스크래핑한 베어러 토큰을 요구하고, 이를 재생해야 합니다. 리뷰는 대략 20개씩 묶음으로 제공되며, offset으로 더 깊이 페이지네이션합니다; 오프셋이 클수록 리뷰가 오래된 경향이 있습니다, 왜냐하면 Apple은 이 엔드포인트가 날짜별로 직접 정렬하는 것을 허용하지 않기 때문입니다.
여기서 진짜 제약은 속도 제한이며, 단일 IP에서 빠르게 도착합니다. 해결책은 마법이 아닙니다 - 고의적인 지연과 지수적 백오프, 그리고 IP 전반에 걸쳐 요청을 분산하는 것입니다. 둘 다 추가한 실무자들은 제한기에 걸리지 않고 하나의 앱에서 약 15,000개의 리뷰를 가져왔습니다. 이것이 바로 회전 주거용 풀이 가치가 있는 이유입니다: 각 묶음은 다른 깨끗한 IP에서 나올 수 있어, IP당 카운터가 차단 영역으로 올라가지 않습니다.
import time, requests
# token is scraped once from the app's App Store web page, then reused
HEADERS = {"Authorization": "Bearer TOKEN_FROM_APP_PAGE",
"Origin": "https://apps.apple.com"}
def apple_deep_reviews(app_id, country="us", target=2000):
reviews, offset = [], None
while len(reviews) < target:
params = {"l": "en-US", "offset": offset} if offset else {"l": "en-US"}
url = (f"https://amp-api.apps.apple.com/v1/catalog/{country}/apps/"
f"{app_id}/reviews")
proxy = f"http://USER:PASS@rotating.quantumproxies.io:8000"
r = requests.get(url, headers=HEADERS, params=params,
proxies={"https": proxy}, timeout=25)
if r.status_code == 429: # rate limited
time.sleep(8); continue # back off, gateway rotates the IP
data = r.json()
reviews += data.get("data", [])
offset = data.get("next", "").split("offset=")[-1] or None
if not offset:
break
time.sleep(1.5) # be a polite client
return reviews

Google Play: HTML이 아닌 수화된 JSON
Play 리뷰는 페이지 HTML에 있지 않습니다. 스토어는 내부 배치 엔드포인트를 통해 이를 로드하며, 중첩된 JSON을 반환하고, 페이지 번호가 아닌 연속 토큰으로 페이지네이션하며, 정렬 순서(최신, 평점, 유용성)로 필터링합니다. 이러한 요청을 수동으로 재구성하는 것은 번거로우므로, 대부분의 팀은 엔드포인트를 래핑하고 country 및 lang 매개변수를 노출하는 잘 유지된 오픈 소스 google-play-scraper 라이브러리(Node 및 Python)에 의존합니다. Apple과 마찬가지로, 국가별 결과가 다르므로 둘 다 명시적으로 설정하세요.
# pip install google-play-scraper
from google_play_scraper import reviews, Sort
result, token = reviews(
"com.example.app",
lang="en", # review language
country="us", # storefront
sort=Sort.NEWEST,
count=200, # per call; loop with continuation_token for more
)
for r in result[:3]:
print(r["score"], r["reviewCreatedVersion"], r["content"][:80])
실제 볼륨에서 Play 엔드포인트는 IP별로 제한하며, JSON 구조는 주기적으로 변합니다. 유지 관리를 원하지 않는다면, 수화된 데이터를 깨끗한 JSON으로 렌더링하고 반환하는 Scraper API가 두 문제를 제거합니다 - 이는 프록시 및 구문 분석을 수행하므로 안정적인 형태를 소비할 수 있습니다. 대규모로 제품 리뷰를 스크래핑하는 데 설명한 동일한 트레이드오프 논리가 여기에 직접 적용됩니다.
한 필드 쌍이 사람들을 혼란스럽게 합니다: 언어와 국가는 동일한 노브가 아닙니다. 스토어프론트(국가)는 어떤 리뷰가 존재하는지를 결정하고; 언어 매개변수는 그 중 어떤 것을 반환받는지를 결정합니다. 캐나다나 스위스와 같은 이중 언어 시장에서는 종종 두 언어 모두를 원하므로, 국가가 단일 언어를 의미한다고 가정하기보다는 독립적으로 설정하세요. Apple 측에서는, 더 풍부한 기록이 개발자 응답도 노출합니다 - 리뷰 아래에 공급업체가 게시하는 공개 답변 - 이는 경쟁자가 불만을 어떻게 분류하고 어떤 문제를 공개적으로 답변하기로 선택하는지를 보여주는 조용히 가치 있는 신호입니다.
지역 스토어프론트가 핵심입니다
두 스토어 모두 국가 스토어프론트에 의해 조직되며, 두 글자 코드로 키가 지정됩니다. 앱의 미국 리뷰는 독일, 일본, 브라질에서 어떻게 받아들여지는지에 대해 아무것도 알려주지 않습니다 - 다른 언어, 다른 불만, 다른 기능 격차. 각 스토어프론트를 정직하게 읽으려면 해당 국가의 출구 IP에서 요청해야 합니다; 잘못된 지역의 데이터센터 IP는 일관성이 없거나 차단된 응답을 가져옵니다. 200개 이상의 국가에 걸친 주거용 출구를 통해 동일한 앱을 모든 시장에 반복하여 국가별 감정 지도를 구축할 수 있습니다 - 진지한 ASO 작업의 원재료입니다.

리뷰에서 ASO 신호로
추출은 지루한 절반입니다. 보상은 그 위에 계산하는 것입니다: 반복되는 테마로 리뷰 텍스트를 클러스터링하고, 앱 버전별 감정을 추적하여 평점을 떨어뜨린 릴리스를 포착하고, 경쟁자를 감시하여 제품이 이미 답하는 기능 요청을 찾고, 스토어프론트 전반에 걸쳐 불만 패턴을 비교합니다. 모든 리뷰를 version 필드에 연결하면 분석 대시보드가 제공하지 않는 회귀 타임라인을 얻을 수 있습니다. 관련된 평판 작업 - Trustpilot 리뷰 마이닝 - 은 전체 고객 목소리 그림을 위해 앱 스토어 데이터와 깔끔하게 쌓입니다.
자주 묻는 질문
파이썬으로 앱 스토어 리뷰를 어떻게 스크래핑하나요?
Apple의 공개 RSS 고객 리뷰 JSON 피드로 시작하세요 - 토큰 없이, 구조화된 출력, 하지만 앱당 스토어프론트당 약 500개의 최신 리뷰로 제한됩니다. 더 깊이 들어가려면, 앱의 웹 페이지에서 스크래핑한 베어러 토큰으로 AMP 앱 스토어 API를 호출하고, offset으로 페이지네이션하며, 지연 및 백오프를 추가하세요. 각 스토어프론트를 해당 국가의 주거용 IP를 통해 라우팅하세요.
공식적인 앱 스토어 리뷰 API가 있나요?
Apple의 공개 RSS 피드는 공식적이고 토큰이 없는 리뷰 소스와 가장 가깝지만, 제한이 있습니다. 더 풍부한 AMP 엔드포인트는 스토어의 자체 웹 페이지가 사용하는 것이며, 스크래핑한 베어러 토큰이 필요합니다. 둘 다 대량의 타사 리뷰 수집을 위한 문서화된 개발자 제품이 아니므로, 속도 제한 및 조건을 신중하게 다루세요.
Google Play 리뷰를 어떻게 스크래핑하나요?
Play는 내부 배치 엔드포인트에서 중첩된 JSON을 반환하며, 연속 토큰으로 페이지네이션되고 정렬 순서로 필터링된 리뷰를 제공합니다. 유지 관리된 오픈 소스 google-play-scraper 라이브러리가 이를 래핑하고 country 및 lang을 노출합니다. 둘 다 설정하고, 볼륨을 위해 연속 토큰을 반복하며, 엔드포인트가 주소별로 제한하기 때문에 요청을 IP 전반에 걸쳐 분산하세요.
앱 리뷰를 스크래핑하는 데 왜 프록시가 필요한가요?
두 가지 이유입니다. 속도 제한: 두 스토어 모두 단일 IP를 빠르게 제한하므로, 회전 주거용 출구는 IP당 카운터를 충분히 낮게 유지하여 수천 개의 리뷰를 가져올 수 있습니다. 지리: 리뷰는 스토어프론트별로 특정하므로, 국가의 리뷰를 정확하게 읽으려면 해당 국가의 IP에서 요청해야 합니다. 잘못된 지역의 데이터센터 IP는 일관성이 없거나 차단된 응답을 가져옵니다.
앱 스토어 데이터는 세 가지 간단한 장애물 - 제한, 토큰 및 스토어프론트 - 로 막힌 금광입니다. 어떤 엔드포인트를 타격할지 알고, 올바르게 페이지네이션하고, 깨끗한 IP로 올바른 국가에서 나가면, 흩어진 별점 평가를 버전별, 시장별 고객 목소리 피드로 전환할 수 있습니다.