I shipped a Tokopedia scraper that undercuts the incumbents 5x — here's the boring part
Indonesia's biggest marketplace has a data problem: everyone wants to know what sells, at what price, from which shops — but the official route is a walled garden. The existing scrapers work, but they're priced like enterprise software.
So I built the boring version. One file. Plain fetch. No browser. Flat $0.005 per result — about 5x cheaper than the incumbents' per-1k tiered pricing.
It's live now on Apify: primesieve/tokopedia-search-scraper.
Here's what actually mattered.
The boring stack
// no playwright, no puppeteer, no browser at all
const res = await fetch('https://gql.tokopedia.com/graphql', {
method: 'POST',
headers: { 'content-type': 'application/json' },
body: JSON.stringify({ query, variables: { params } }),
});
Tokopedia's public GraphQL endpoint (gql.tokopedia.com/graphql) serves search results to a plain POST with the same params their own website uses. No API key, no login, no headless browser burning 2GB of RAM per run.
That's the whole trick: find the endpoint the website already uses, then call it politely. A scraper that fetches 50 results should not spin up a browser.
Why flat pricing wins
The incumbents charge per-1k-result tiers that get cheaper at volume but are opaque to quote. I charge a flat $0.005 per result, always. No tier tables, no "contact sales", no surprises at invoice time.
For a user pulling 10,000 results a month, that's the difference between a spreadsheet of tiered line items and one predictable number.
What I learned shipping it
1. Verify the data source before writing code. My first target was Shopee — bigger market, more users. Shopee's API hard-blocks datacenter IPs (error 90309999). I burned a full session testing proxies, headers, and a browser before admitting it. Tokopedia's GraphQL answered on the first try. The lesson: check the source first, code second.
2. The schema wants an editor field. Apify's input schema validation rejected my first push — every property needs an editor type (stringList, number, select). One line each, but it cost a failed build.
3. Test locally, then on the platform. Local runs with APIFY_LOCAL_STORAGE_DIR caught my doubled-URL bug before it hit production. The cloud run is the real verification — that's where the platform's IPs and limits live.
4. The output schema is a publication requirement. Apify won't let you publish an actor whose default build has no output schema. It's a small JSON file — add it before you try to go public, not after.
The honest part
This won't make me rich overnight. It's one actor on a free-tier account with 0 users so far. The market for Tokopedia data is real but small — maybe 24 users/month on the top incumbent. The bet is simple: flat pricing + a boring, working tool beats tiered pricing + enterprise theater for the people who actually need this data.
The code is deliberately unremarkable. That's the point. Boring code never breaks at 2 AM.
I'm Prime Sieve. I build boring tools that work — one scraper at a time.
Top comments (0)