Pinkoi Scraper - Product, Price & New Listing Watch
Pricing
from $0.69 / 1,000 product scrapeds
Pinkoi Scraper - Product, Price & New Listing Watch
Pinkoi scraper: search keywords or shop ids to one row per listing with price and original price in 12 currencies (USD, JPY, TWD...), discount, rating, reviews, shop, photo, workshop and digital flags. For design-marketplace price and new-listing watching.
Pricing
from $0.69 / 1,000 product scrapeds
Rating
0.0
(0)
Developer
Superslow Sloth
Maintained by CommunityActor stats
0
Bookmarked
2
Total users
1
Monthly active users
5 days ago
Last modified
Categories
Security
Limited permissionsShare
This Pinkoi scraper searches Pinkoi, Asia's
cross-border design marketplace, by keyword or by shop and returns one flat row
per listing: the title, link and photo, the shop, the current price and the
price before the shop's discount in the currency you choose (twelve,
including USD, JPY, TWD, EUR and GBP), the discount in percent, rating, review
count, badges, whether the row is a sponsored slot, and whether it is an
ordinary product, a workshop or a digital download. Run it on a schedule with
the sort set to Newest and diff product_id against the last run to get a
new-listing watch for a keyword or a shop; run it with a fixed shop and
keyword and diff price to get a price watch.
No account, no API key, no login, no browser. One request returns up to 60 rows.
Input
| Field | Notes |
|---|---|
searchTerms | One or more search terms, one per line (tote bag, ceramic mug, 帆布袋). Each is searched across all of Pinkoi. A listing found by two terms is returned once, under the first. |
shopIds | One or more shops, one per line, whose whole catalogue you want. The ID is the end of the shop's address: omhandmade for https://www.pinkoi.com/store/omhandmade (the full address is accepted). With search terms as well, each term is searched inside each shop. |
maxItems | Listings to return per term or shop (default 100, up to 10,000). The prefilled 30 is one page. |
sort | popular (Pinkoi's default), newest, price-asc, price-desc: the choices of Pinkoi's own sort menu. |
currency | The currency of every price: USD (default), TWD, JPY, EUR, GBP, HKD, CNY, THB, SGD, MYR, AUD or CAD. |
language | The language of titles and shop names and of the product links: en (default), zh-TW, zh-CN, zh-HK, ja or th. |
includeSponsored | On by default. Turn it off to return only organic listings; the sponsored rows skipped are not charged and do not count toward maxItems. |
proxyConfiguration | Apify datacenter proxy by default. |
Give search terms, shop IDs or both. Example input:
{"searchTerms": ["tote bag"],"shopIds": ["omhandmade"],"sort": "newest","currency": "JPY","language": "ja","maxItems": 50}
Output
Prices are numbers in the currency you chose; currency repeats its code on
every row.
| Field | Notes |
|---|---|
query, shop_filter, position | The term that found the listing (null when a whole shop was read), the shop the search was limited to (null for a search across Pinkoi), and the listing's place in Pinkoi's list for that term, shop and sort. 1 is first. It counts every row of the pages read, sponsored rows included, so it is the slot a visitor sees. |
product_id, url, image_url | Pinkoi's product id (7gYh5EN3), the product page on the host of your language, and the first photo (500 px wide JPEG). |
name | The listing title in your language. Line breaks inside a title are collapsed to a space. |
shop_id, shop_name | The shop's id (what shopIds takes) and its name. |
kind | product, workshop (an experience or class, Pinkoi's "Workshop" badge) or digital (a downloadable file). |
workshop_location | Where a workshop takes place (Taipei City). Null for other kinds. |
currency, price | The ISO code you asked for, and the current price in it. |
original_price, on_sale | The price before the shop's discount, and whether it is above price. |
discount_percent | (1 - price / original_price) * 100, one decimal place. Worked out from the two prices, not sent. Null when not on sale, never 0. |
rating, review_count | The average stars (1 to 5, one decimal) and the number of reviews. Both null for a listing with no reviews. |
has_video | True when the listing has a video. |
badges | Pinkoi's feature badges as codes: customize, exclusive, eco, readytobuy ("N people are about to buy", which changes by the hour), social_good. An empty list when there are none. |
is_sponsored | True when the row was a sponsored slot. |
category_id, subcategory_id | Pinkoi's category numbers. Pinkoi sends no category name. |
Example row (real values, 2026-11-02):
{"query": "tote bag","shop_filter": null,"position": 67,"product_id": "Tr8iP5Kw","name": "【MOOMIN】Canvas Multi-Pocket Tote Bag","url": "https://en.pinkoi.com/product/Tr8iP5Kw","image_url": "https://cdn01.pinkoi.com/product/Tr8iP5Kw/0/2/500x0.jpg","shop_id": "yoshi850","shop_name": "Iam select shop","kind": "product","currency": "USD","price": 19.2,"original_price": 28.81,"on_sale": true,"discount_percent": 33.4,"rating": null,"review_count": null,"has_video": false,"badges": [],"is_sponsored": false,"category_id": 1,"subcategory_id": 104,"workshop_location": null}
Sponsored rows, repeats and order
Pinkoi mixes sponsored listings into its results: a page is 30 organic products plus up to 30 sponsored ones (60 rows), and later pages carry fewer as the ad pool runs out. The same product can appear twice on a page, once sponsored and once organically (all 12 products of one small shop came back twice). Each product is returned once: as the organic row when a page has both, otherwise the first sighting. The repeats are not charged.
Pinkoi's order is not fixed. Two requests for the same search list slightly
different rows in a slightly different order, and the match count drifts by a few
(tote bag read 21,792 to 21,800 over a handful of requests). Positions are the order
of the run that produced them. The price sorts are Pinkoi's own and not exact:
in a sample of 160 organic rows, 16 neighbouring pairs were out of order
ascending and 44 descending.
Currency
Pinkoi picks the currency from the country of the visitor, and a guest cannot change it on the site, so a scraper behind a proxy would get the proxy's currency: yen from Japan, US dollars from the United States. This actor always asks for the currency you chose and checks that every price came back in it; a page priced in another currency is refused and retried, never written under the wrong code. Prices are Pinkoi's own conversion, so the same listing in two currencies is two numbers, and a listing's price can move with the exchange rate without the shop changing anything. For a price watch keep the currency fixed.
Honest nulls
A field Pinkoi did not send is null, never 0 or "". badges is an empty
list when there are none.
pricecan really be 0. A digital listing priced at 0.00 with anoriginal_priceabove it is free (discount_percent100). Pinkoi sends it.- No listing date. Pinkoi's search list carries no creation date, so
newestis Pinkoi's own "Most recent" order, which the data cannot be used to check (the sponsored slots at the top of a page stay the same under every sort). A new-listing watch is a diff ofproduct_idbetween runs. - No stock, no description, no variants. Pinkoi's search list carries neither; a row is a listing at its listed price.
- No shipping information. Pinkoi's free-shipping badge depends on the visitor's country (10 of 60 rows from a Japanese address, none from an Apify datacenter address), so it is not reported.
Pricing
Pay per event:
- $0.002 per run (
actor-start), charged only after your input is validated, so a run that fails on bad input costs nothing. - $0.000693 per product written (
product-scraped), i.e. $0.693 per 1,000 listings. A row that is not written is not charged: sponsored rows skipped byincludeSponsored, and repeats of a product already returned, are free.
How it fetches
Pinkoi's search pages answer a script with a "Please wait" challenge (HTTP 403).
The page fills its list from a JSON service,
/apiv3/search/search_product, which needs no key, cookie or login and which
this actor reads directly. Measured 2026-11-02: it answers JSON to a plain
connection in Japan, to an Apify datacenter address (10 of 10 in the build
probe), to the residential group (10 of 10, and 10 of 10 pinned to Japan) and to
the platform's own address. A refusal (403, 429,
5xx), a 200 that is not Pinkoi's answer, or prices in the wrong currency is
treated as the address being blocked, and the actor rotates to a fresh one and
retries.
Things worth knowing, all measured:
- The language is the host, not a setting.
en.pinkoi.com,www.pinkoi.com(Traditional Chinese, Taiwan),cn.,hk.,jp.andth.search the same catalogue; the language input picks the host and so the titles and the links. - A shop is a filter.
shopIdslimits the search to one shop's listings (omhandmade: 4,103 listings; withlinen, 764 of them). A shop that does not exist is an empty answer, logged, not an error and not charged. Shop IDs are lower case and exact. - Depth. Pinkoi answers up to page 1,000 (page 1,001 is refused with
search_exceed_max_window_limit). The actor stops there and says so in the log. A page past the last real page is an empty list. At most 10,000 listings per term or shop; a broad term can match more than 100,000 listings, so narrow it with a shop or a more specific term. - Photos. The photo is built from the listing id and the image revision the list sends; the 40 tried (22 different revisions) all answered with a JPEG.
If Pinkoi changes its search service, the run fails with a message instead of returning empty rows.