How to use Amazon Product & Best Sellers Scraper
Step by step: in the Apify Store, over the API, from JavaScript or Python, in n8n, and from AI agents through MCP or LangChain.
$0.54 per 1,000 search results (live Apify price on 2026-11-01).
1. In the Apify Store (no code)
- Open arcadium/amazon-products and sign in to Apify (a free account works).
- Fill in the input form. The fields below are the ones the example uses.
- Set a maximum cost per run in the run options if you want a hard cap.
- Start the run. Rows appear in the Output tab as they arrive.
- Export the dataset as JSON, CSV or Excel, or connect an integration.
| Input field | Type | Description |
|---|---|---|
searches | array | Keywords to search on the chosen store, e.g. ["wireless earbuds", "usb c cable"]. Each term gives up to maxResultsPerSearch result rows in Amazon's order: position, sponsored flag, ASIN, title, price, list price, rating, rating count, badges, bought in past month. Also read from keywords, searchQueries, searchQuery or queries (other Amazon actors' names). |
categories | array | Category paths as in the store's Best Sellers URLs, e.g. ["electronics", "electronics/172541", "kitchen"] (amazon.de: "ce-de"). Each category gives one ranked list per listTypes entry, up to maxResultsPerList ranks. A Best Sellers URL works here too. |
asins | array | Product ids, e.g. ["B0DCH8VDXF", "B08JHCVHTY"]. Each gives one product row: title, image, rating, star split, rating count, Buy Box price and seller, list price, ships from, delivery promise, and the other offers (condition, price, seller). |
urls | array | Any mix of search URLs (https://www.amazon.com/s?k=yoga+mat, filters kept), Best Sellers / New Releases / Movers & Shakers URLs (https://www.amazon.de/gp/bestsellers/kitchen) and product URLs (https://www.amazon.co.uk/dp/B0DCH8VDXF). Each URL is read on its own store. |
marketplace | string | Store for searches, categories and ASINs (URLs use their own store). Prices, sellers and delivery are those a shopper in that country sees: non-US stores are read from an IP in their country. Example: DE. Lowercase codes (us, uk, de) and the names country, countryCode, amazonDomain or website are accepted too. |
maxResultsPerSearch | integer | Result rows per search term or search URL, 1 to 1,000 (default 48). Amazon shows 16-60 cards per page; the actor reads as many pages as needed. Sponsored cards count unless includeSponsored is off. Also read from maxResultsPerKeyword or maxResultsPerQuery. |
includeSponsored | boolean | Keeps sponsored (ad) cards in search results, flagged with sponsored: true. Turn off to get organic results only; skipped ads are free. Default: true. excludeSponsored: true (another actor's name) means the same as false here. |
Example input:
{
"searches": [
"wireless earbuds"
],
"categories": [],
"asins": [],
"urls": [],
"marketplace": "US",
"maxResultsPerSearch": 20,
"includeSponsored": true
}
2. Over the Apify API
The synchronous endpoint runs the actor and returns its rows in one call (for runs up to about five minutes; use the asynchronous run endpoint for longer ones).
curl -X POST "https://api.apify.com/v2/acts/arcadium~amazon-products/run-sync-get-dataset-items" \
-H "Authorization: Bearer $APIFY_TOKEN" \
-H "Content-Type: application/json" \
-d '{"searches":["wireless earbuds"],"categories":[],"asins":[],"urls":[],"marketplace":"US","maxResultsPerSearch":20,"includeSponsored":true}'
3. From JavaScript
// npm install apify-client
import { ApifyClient } from 'apify-client';
const client = new ApifyClient({ token: process.env.APIFY_TOKEN });
const run = await client.actor('arcadium/amazon-products').call({
"searches": [
"wireless earbuds"
],
"categories": [],
"asins": [],
"urls": [],
"marketplace": "US",
"maxResultsPerSearch": 20,
"includeSponsored": true
});
const { items } = await client.dataset(run.defaultDatasetId).listItems();
console.log(items);
4. From Python
# pip install apify-client
import os
from apify_client import ApifyClient
client = ApifyClient(os.environ["APIFY_TOKEN"])
run = client.actor("arcadium/amazon-products").call(run_input={
"searches": ["wireless earbuds"],
"categories": [],
"asins": [],
"urls": [],
"marketplace": "US",
"maxResultsPerSearch": 20,
"includeSponsored": True,
})
items = client.dataset(run.default_dataset_id).list_items().items # apify-client 3.x returns a Run object
print(items)
5. In n8n
Paste this node into a workflow (it is a plain HTTP Request node). Create a Header Auth credential with name Authorization and value Bearer <APIFY_TOKEN>; each returned row becomes one item for the next node.
{
"nodes": [
{
"name": "Run arcadium/amazon-products",
"type": "n8n-nodes-base.httpRequest",
"typeVersion": 4,
"position": [
0,
0
],
"parameters": {
"method": "POST",
"url": "https://api.apify.com/v2/acts/arcadium~amazon-products/run-sync-get-dataset-items",
"authentication": "genericCredentialType",
"genericAuthType": "httpHeaderAuth",
"sendBody": true,
"specifyBody": "json",
"jsonBody": "{\"searches\":[\"wireless earbuds\"],\"categories\":[],\"asins\":[],\"urls\":[],\"marketplace\":\"US\",\"maxResultsPerSearch\":20,\"includeSponsored\":true}",
"options": {
"timeout": 300000
}
}
}
],
"connections": {}
}
6. From an AI assistant (MCP)
Add Apify’s MCP server to Claude Desktop, Cursor, VS Code or any MCP client, limited to this actor:
{
"mcpServers": {
"apify": {
"url": "https://mcp.apify.com/?tools=arcadium/amazon-products",
"headers": {
"Authorization": "Bearer <APIFY_TOKEN>"
}
}
}
}
More on the MCP page.
7. From LangChain
# pip install langchain-apify (reads APIFY_API_TOKEN from the environment)
from langchain_apify import ApifyActorsTool
tool = ApifyActorsTool("arcadium/amazon-products")
rows = tool.invoke({"run_input": {
"searches": ["wireless earbuds"],
"categories": [],
"asins": [],
"urls": [],
"marketplace": "US",
"maxResultsPerSearch": 20,
"includeSponsored": True,
}})
# or give `tool` to an agent: create_react_agent(llm, [tool])
Sample output
One row, from the example in the actor’s README. Long text is shortened and lists are cut to two items.
{
"rowType": "searchResult",
"marketplace": "US",
"domain": "amazon.com",
"currency": "USD",
"searchTerm": "wireless earbuds",
"page": 1,
"position": 2,
"organicPosition": null,
"asin": "B0C1BTXM9W",
"sponsored": true,
"title": "Wireless Earbuds, Bluetooth 5.4 Ear Buds LED Power Display Headphones Bass Stereo ...",
"url": "https://www.amazon.com/dp/B0C1BTXM9W",
"imageUrl": "https://m.media-amazon.com/images/I/614gb9uXQuL.jpg",
"price": 19.99,
"priceText": "$19.99",
"listPrice": 28.49,
"listPriceText": "$28.49",
"rating": 4.3,
"ratingCount": 14589,
"badges": [],
"boughtPastMonth": 6000,
"boughtPastMonthText": "6K+ bought in past month",
"deliveryText": "Join Prime to get FREE delivery Tomorrow, Oct 23",
"scrapedAt": "2026-10-22T08:00:00.000Z"
}
| Field | What it holds |
|---|---|
rowType | Kind of row. Filter on this first. 'searchResult': one search result card (charged as search-result). 'bestseller': one entry of a Best Sellers, New Releases, Movers & Shakers, Most Wished For or Gift Ideas list (charged as bestseller). 'product': one light product row with Buy Box and offers (charged as product). 'error': an input that gave no data; see code and message (free). |
marketplace | Country code of the Amazon store, e.g. US, DE, JP. |
domain | Store domain, e.g. amazon.de. |
currency | Currency of every price on the row, e.g. USD, EUR, JPY. |
asin | Amazon product id (10 letters and digits), e.g. B0DCH8VDXF. |
url | Canonical product link https://www.amazon.<store>/dp/<ASIN>. |
title | Product title as the store shows it. Null on rank-only list entries (detailsComplete false). |
imageUrl | Main product image, full size. |
price | Search and list rows: price shown on the card, as a number in the store's currency (e.g. 19.99). Null when the card shows no price (unavailable, variants only). |
priceText | Price exactly as shown, e.g. '$19.99', '€27,99', '¥8,990'. |
listPrice | Search rows: struck-through list or typical price, when shown. Product rows: the Buy Box offer's reference price ('List Price', 'Was', 'RRP'). |
listPriceText | Reference price exactly as shown. |
rating | Average star rating, 0 to 5, e.g. 4.5. Null when the product has no ratings. |
ratingCount | Number of ratings (global ratings on product rows). |
searchTerm | Search rows: the search term (or the URL's keyword) the card came from. |
page | Search rows: results page of the card (1-based). |
position | Search rows: 1-based position over all pages, sponsored cards included (the order a shopper sees). |
organicPosition | Search rows: 1-based position among non-sponsored results; null for sponsored cards. |
sponsored | Search rows: true for sponsored (ad) cards. |
badges | Search rows: badges on the card, e.g. 'Best Seller', "Amazon's Choice", 'Overall Pick', 'Limited time deal'. |
boughtPastMonth | Search rows: lower bound from 'bought in past month' (e.g. 1000 for '1K+'). Null when not shown. |
boughtPastMonthText | Search rows: the 'bought in past month' text as shown. |
deliveryText | Search rows: first delivery line, e.g. 'FREE delivery Mon, Oct 26'. |
listType | List rows: bestsellers, new-releases, movers-and-shakers, most-wished-for or most-gifted. |
category | List rows: category path as in the list URL, e.g. 'electronics/172541'; empty for the all-departments list. |
categoryName | List rows: category name as shown, e.g. 'Electronics'. |
listTitle | List rows: page heading, e.g. 'Best Sellers in Electronics'. |
rank | List rows: rank in the list (1 = top). |
rankChangePercent | Movers & Shakers rows: sales-rank gain over the past 24 hours in percent (e.g. 1250). Null on other lists. |
salesRank | Movers & Shakers rows: sales rank now. Null on other lists. |
salesRankYesterday | Movers & Shakers rows: sales rank 24 hours ago. Null on other lists. |
detailsComplete | List rows: false when Amazon gave only the ASIN and rank for the entry (title, price and rating null). |
starPercent | Product rows: share of ratings per star in percent, e.g. {"5": 73, "4": 12, "3": 8, "2": 2, "1": 5}. Null without ratings. |
hasBuyBox | Product rows: true when Amazon shows a featured offer (Buy Box). False for 'No featured offers available'. |
buyBoxPrice | Product rows: price of the featured (Buy Box) offer, as a number. |
buyBoxPriceText | Product rows: Buy Box price exactly as shown. |
listPriceLabel | Product rows: label of the reference price, e.g. 'List Price:', 'Was:', 'RRP:'. |
buyBoxCondition | Product rows: condition of the featured offer, e.g. 'New', 'Used - Like New'. |
buyBoxSeller | Product rows: business name of the Buy Box seller, e.g. 'Amazon.com' or a merchant name. |
buyBoxSellerId | Product rows: Amazon merchant id of the Buy Box seller (e.g. A3US3KTV1R02M4); null when Amazon sells it. |
buyBoxShipsFrom | Product rows: who ships the Buy Box offer, e.g. 'Amazon.com'. |
buyBoxFulfilledByAmazon | Product rows: true when Amazon ships the Buy Box offer (FBA or Amazon itself). |
buyBoxDelivery | Product rows: delivery promise of the Buy Box offer, e.g. 'FREE delivery Tuesday, October 27'. |
otherOfferCount | Product rows: number of other offers Amazon lists besides the Buy Box. |
offers | Product rows: other offers (up to maxOffers), each with condition, price, priceText, listPrice, soldBy (business name), sellerId, shipsFrom, fulfilledByAmazon, sellerRating, sellerRatingCount, sellerPositiveText, deliveryText, conditionNote. |
source | Product rows: the ASIN, URL, search term or list the product came from. |
scrapedAt | When the row was read, ISO 8601 UTC. |
input | Error rows: the search term, category, ASIN or URL that gave no data. |
code | Error rows: not_found, no_match, invalid_input, blocked or unavailable. |
message | Error rows: what happened, in plain words. |
platform | Error rows: always 'amazon'. |
Tutorials
Schedule it
In Apify Console, create a Task from your input and add a Schedule (for example daily). Each run writes a new dataset; integrations can push the rows to Google Sheets, Slack, a webhook or your database.