The Marketplace and List dropdowns accept null as well, so an all-fields-null template runs.
- An input that fills every optional field with
null now starts. That is the shape n8n, Make and most agent frameworks actually send, and two fields were still refusing it: the Marketplace and List dropdowns. {"categories": ["electronics"], "marketplace": null, "list": null, "maxItems": null} used to be rejected before the run began, with an error about allowed values. It now runs on the defaults — amazon.com, Best Sellers — exactly as if those fields had been left out.
- A value the dropdown does not list is answered by name, and nothing is read.
"list": "movers-and-shakers" is the one a buyer actually types, and Best Sellers rows delivered under that heading would read exactly like the answer they asked for. It now returns one uncharged row naming the three lists this actor reads, and reads nothing. Same for a store we do not cover. Nothing is charged, and the run still succeeds.
- Every value the dropdowns list behaves exactly as before, and the console pickers are unchanged.
- The run's own status line now says "1 input error" instead of "1 category line could not be read". A mistyped
list was being reported as a category problem, which sent you looking at the wrong box; the dataset row has always named the right one.
- Nothing about what is delivered or charged changed. One flat fee per delivered rank, misses never charged.
Optional settings now accept null, and null means "use the default".
- An explicit
null on an optional setting starts the run instead of refusing it. Agents and integrations routinely fill in the fields they are not using with null; until now {"categories": ["electronics"], "maxItems": null} was rejected before the run began, with an error saying the field had to be an integer. It now runs exactly as if the field had been left out.
null never changes what a run does. Max products per category, Max products (whole run), Max run seconds, Include variants and Include specifications each fall back to the same default they would have used anyway. This is a second way to say "leave it alone", not new behaviour.
Categories still cannot be null, and neither can the Marketplace and List dropdowns — a dropdown only accepts one of the values it lists. Send a real value or leave the field out entirely. Categories staying strict is deliberate: it is what catches a mistyped field name before the run starts rather than after.
- Nothing about what is delivered or charged changed. One flat fee per delivered rank, misses never charged.
Rows now arrive in rank order, the way this page has always described them.
- The dataset is written in rank order — 1, 2, 3 — and stays that way. Two products are fetched at a time, and until this release each one was written the moment its own page came back, so a fast rank #4 could land above a slow rank #2. The ranks were always correct on the rows themselves; only the order they were written in was not. Rows are now written in rank order while the fetching still runs side by side, so the run is no slower.
- An uncharged miss sits in its own rank slot too, in line with the products around it, instead of at the end. Nothing about what is delivered or charged changed: misses are still never charged, and each delivered product is still one flat fee.
The linked example dataset is re-shot from the code this release ships, and it now has a permanent address.
- The example-dataset link points at a fresh run of exactly this code — the Electronics best sellers, two delivered product rows with the Sold-by cluster populated, the honest uncharged
not_a_product row where Amazon's own subscription plan sits at rank #1, and the summary row last.
- That sample now lives at a permanent address. It used to be one run's own output, which is cleared when that run ages out — the link would eventually have gone dead on its own. It cannot now.
- The page says "one real run of the current code", not "of the current build", because a release that changes only this page must not make that sentence false. Nothing about what this actor delivers or charges changed in this release.
The linked example dataset is re-shot from a verified run of the current build, and one status-line wording is corrected.
- The example-dataset link now points at a run of this build — the Electronics best sellers with the Sold-by cluster populated on delivered rows, the honest uncharged
not_a_product row at rank #1, and the summary row last.
- Status-line grammar: a single permanent miss now reads "1 product was not a deliverable product listing" instead of the plural form. Nothing about what this actor delivers or charges changed in this release.
Ranked rows carry their Sold-by seller and their specs again — the two gaps that hit device-heavy categories hardest.
buyBoxSeller, buyBoxSellerId, fulfilledByAmazon and soldByAmazon are filled in again. Amazon serves the Sold-by block in several layouts and ranked rows had been shipping the cluster as null; the parser now reads all of them, verified against freshly captured pages.
- Amazon's own device pages now deliver their specs. Best-seller lists are full of Amazon devices, whose pages keep the spec sheet in a different layout — those rows previously shipped
specs: {}. categoryPath and bestSellersRank stay empty on those pages because Amazon renders neither there; the README now discloses that.
- The
‎Apple brand garbage is gone. Invisible direction marks some pages prefix onto brand and spec values are stripped from every text field.
- New column:
buyBoxNote. When a served page genuinely names no seller, the Sold-by fields stay null and this column says so on that exact row.
- The run's status line now separates permanent misses from temporary ones. A rank held by something that is not a product listing (Amazon's own subscription plans, for one) no longer reads "could not be fetched" as if a re-run would fix it.
- amazon.co.uk lists deliver again — the fetch ladder gained a final mobile-fingerprint step on the same residential exits after .co.uk began refusing every desktop fingerprint. Nothing about what is charged changed: misses are never charged.
Clearer release notes — this page's notes now read more plainly. Nothing about what this actor delivers or charges changed.
Every actor named in the README is now a live link.
- The steadyfetch shelf links point at the published actors. The Amazon Seller Scraper entry and every other name in the suite tables now link to their live store pages. Nothing about what this actor delivers or charges changed.
Restarts, resurrections and billing bookkeeping hardened end to end.
- A restarted run no longer trusts a stale answer about what it already delivered. Right after a restart, the platform's view of the run's own output can lag a few seconds behind. A run that believed that lagging answer could have delivered — and charged — products a second time, or lost count of rows past the lagging total. It now double-checks an "empty" answer and reads its own output through to the true end before doing anything, so nothing already delivered is ever fetched, delivered or billed again.
- Finishing an interrupted charge can never bill twice — and can never sink the run. When a restart finds a charge from the previous attempt half-finished, the amount still owed is reckoned against the highest count of what already landed, so a lagging counter cannot cause a repeat charge. And if that settlement cannot be completed at that moment, the run carries on and settles it on a later resume instead of failing — nothing extra is charged either way.
- A run being moved to another server hands over cleanly. The departing side no longer declares the run finished on its way out — the run continues where it left off.
- A resurrected run gets a real working window. "Max run seconds" counts the run's life, not each restart's — but a run resurrected after that window had already passed used to stop on its first step, blaming your own limits, with nothing new delivered. It now gets a fresh, bounded window to finish the remaining work.
- If this actor's own price configuration is ever broken, a run stops before spending anything. Both broken shapes — one that would bill for rows we promise carry no result fee, and one that could not bill at all — halt immediately, fetch nothing, charge nothing, and say plainly that the fault is ours.
- A charge is counted only when it actually landed. The
charged flag and the run's own charge totals now reflect the platform's answer, never an assumption.
Numbers printed in the "wrong" language now always read as the numbers they are.
- Counts survive a product page served in another language's number format. Amazon renders a page in the formatting of the route that fetched it, not the store's own, so amazon.de sometimes arrives with English-style numbers — a review count of "4,305". Read with German number rules that used to collapse into a decimal: a charged
reviewCount of 4, a thousand times under. Grouped whole numbers now read as grouped whole numbers in every language — on review counts, list ranks and prices alike.
- "Bought in past month" badges phrased without a "+" right after the digits parse correctly, and the localized German thousand/million marks ("Tsd.", "Mio.") are understood — "Mehr als 1.000 Mal … gekauft" is 1,000, never 1,000,000.
- A Nordic "kr" price mark never takes another marketplace's currency label. When the currency of a price cannot be resolved from the page, the
currency column ships honestly empty instead of guessed.
- The Amazon suite links in the README now point at the published actors.
"Nothing ranked here" now means Amazon really said so.
- A category is never reported as empty on the word of a request Amazon distrusts. Amazon sometimes serves a full "no results" page to a request it does not trust, for a list that in fact has plenty of products. Such a page is now re-checked before any verdict is given, and if that re-check never succeeds the row says the list could not be read this run and asks you to re-run — uncharged. This matters twice over, because an empty-category answer used to be remembered for the rest of the run: a resumed run would not ask again.
- A ranked page we cannot read is reported as our problem, not yours. If Amazon serves a real list page in a layout this actor cannot parse, the row now says so and is flagged for us to look at, rather than claiming the category has nothing ranked on it.
- A list page that redirected to a robot check is read as a robot check even when the destination answers "page not found" — it no longer comes back as "that category page does not exist".
A typo in an input field name now gets a helpful pointer instead of sample rows.
- A run that sets a field this actor does not have is answered, not demoed. Sending something like
depts instead of categories used to look exactly like an empty run, so it came back with the uncharged sample rows — and nothing said the field had been ignored. Such a run now returns one uncharged row that names the field it did not recognise, names Categories (input key categories) and shows the shape to send. A run that really is empty still returns the sample rows, and a run with real categories is unchanged.
Price parsing is hardened, ported from the family's shared parser.
- Promotional wording printed next to a price ("avec 18 % d'économies", "con il 18 % di risparmio") can no longer bleed its digits into the parsed amount — a percentage is never read as part of a price, in any language.
- The Nordic "kr" and Polish "zł" currency marks are now recognised wherever Amazon prints them, instead of being dropped.
- Review counts on European listings are read correctly. Some storefront layouts print the total with a space between the digit groups ("4 298"); earlier builds could not read that formatting and shipped an honest empty
reviewCount. The count now arrives as a number, in the store's own formatting.
- The free sample run survives a restart. Starting the actor with no input returns a small, free, offline sample. If that run was moved to another server or resurrected, it wrote the whole sample into your dataset a second time. It now recognises the rows it has already delivered and adds nothing.
- "Bought in past month" is correct on decimal counts. Amazon writes some of these as
1.5K+, and as 1,5K+ on amazon.de. Both were read as 15,000 instead of 1,500 — ten times the real figure. Whole-number forms such as 2K+ and the German 1.000+ were always right and are unchanged.
One safety rule tightened on the restart path shipped in 1.0.4.
- When a restarted run needs to finish an interrupted charge, it first confirms against the run's own billing record what has already been billed. If that record cannot be read, the run now settles nothing rather than trusting a second source that could be stale. An unbilled row costs us; billing you twice costs you, and only one of those is acceptable.
- The example dataset linked from this page is now a real, unedited run: two departments, three delivered rows, and one uncharged row where Amazon's own subscription plan sits at rank #1.
A run that gets moved between servers no longer repeats or re-charges anything.
- Apify moves long runs to another server and restarts them when it does. Before this build, the restarted run knew nothing about what the first half had already done: it fetched the same ranked products again, wrote them into your dataset a second time, and charged for them a second time. It now re-reads its own results first and picks up at the next rank — no duplicate rows, no second charge, and a resurrected run does the same.
- Your product limit now counts the rows you already have. A run capped at 100 that moves mid-way delivers 100, not 200.
- Your
Max run seconds and our own internal run ceiling are measured from when the run started, not from when it was restarted — so a moved run does not quietly hand itself a second full time budget.
- If a charge was interrupted between a row landing in your dataset and being billed, that single charge is completed on restart, and it can never be made twice. If the run cannot read its own results back at all after a restart, it delivers your rows but bills nothing, and says so.
- A category or a ranked product with a permanent answer — "that department does not exist here", "that page is gone" — is now reported once, not once per restart. Temporary problems are still retried, because a re-run is exactly what they ask for.
- Amazon sells some of its own subscription plans through ordinary product ids, and one of them is rank #1 in the US Electronics chart. Those pages carry no product listing at all, so they used to come back as
parse_failed — "a layout we could not read, that one is on us". They now come back as not_a_product, which is what they are. Still uncharged, either way.
- Amazon's sign-in wall is now detected on every route in one place, including when Amazon redirects to the sign-in page instead of showing the wall. A missed wall used to read as "this category is empty", which is a permanent verdict about your input rather than the temporary block it really is.
- A category page that quietly falls back to Amazon's Best Sellers front page is now recognised from the address it landed on, not only from the page's own navigation — so "that department does not exist in this store" stays accurate when Amazon changes the page.
Review-fix build: billing accuracy, honest statuses, and correct ranks.
- Billing accuracy: when two ranked entries turn out to be the same product — a variant that redirects to one canonical listing — it is delivered and charged exactly once, even when both are fetched at the same moment. A row that fails to be written is no longer counted as delivered, and its charge slot goes back.
- A category link Amazon answers with "page not found" is now a permanent, uncharged answer that tells you to check the slug or paste the link from Amazon's own list. It is no longer retried through every route, and it no longer reads as "temporary — please re-run".
- Rank numbers are read with the store's own number format, so a German list's
1.234 is rank 1,234, and a badge we cannot read comes back empty instead of a wrong-looking number.
- When your spend cap is what stops the run, the summary says so even if the cap runs out on the last category.
Initial release.
- Name an Amazon category and get one complete product row for every rank: the rank, the list, the category and its path, plus price, currency, list price, stock, buy-box seller, rating, review count, bought-in-past-month, variants, bestseller ranks, images, bullet points and the specifications table.
- Best Sellers, New Releases and Most Wished For. Movers & Shakers is not offered because Amazon builds that grid in the browser and the page carries no rows to read.
- 60 ranks per category — ranks 1-30 and 51-80, which is what Amazon puts in the page. Ranks 31-50 and 81-100 are loaded by the browser and are not there to read. Subcategories work as input, and each one is its own list of 60.
- Takes a short department name (electronics, kitchen) or a link copied from the page — both of Amazon's URL shapes, subcategory links included. A pasted link decides its own store and list, so one run can mix stores.
- Marketplaces: amazon.com, amazon.co.uk and amazon.de.
- One priced event per delivered product and nothing else — no start fee, no per-category fee, no per-field fee.
- Full product detail on every rank — there is no cheaper "list only" mode, because that would need a second event and this family charges one.
- Categories that list nothing or are blocked, and individual ranks that cannot be fetched, are returned with an honest status and are never charged, and every run ends with a summary row that reconciles against the invoice.
- Your limits are exact: the run stops cleanly, names the setting that stopped it, and hands back the categories still to do.