Static prices kill affiliate conversions. A "best standing desks" table that says $299 while Amazon shows $349? Your reader bounces. Live data converts β here's how to build a self-updating product feed with Apify actors.
π€ Try it live β chat with a Poe bot that generates the exact pipeline for your niche: Amazon Product Miner Β· Lead List Generator Β· Job Postings Miner Β· SERP Rank Tracker Β· Social Lead Finder
The stack
-
Apify β
apify/amazon-crawlerhandles Amazon's anti-bot wall. Free credits to start. - Nightly schedule β fresh prices every morning, zero maintenance.
Step 1 β Token
Create an Apify account β Settings β Integrations β API token β export APIFY_TOKEN=...
Step 2 β Scrape ASINs in batch
from apify_client import ApifyClient
client = ApifyClient("APIFY_TOKEN")
asins = ["B0ABC12345", "B0DEF67890", "B0GHI11223"]
run = client.actor("apify/amazon-crawler").call(run_input={
"productUrls": [{"url": f"https://www.amazon.com/dp/{a}"} for a in asins],
"proxyCountry": "AUTO_SELECT_PROXY_COUNTRY",
})
for item in client.dataset(run["defaultDatasetId"]).iterate_items():
print(item["asin"], item["title"], item.get("price"), item.get("inStock"))
Fields: asin, title, price, listPrice, stars, reviewsCount, inStock, thumbnailImage, url.
Step 3 β Scheduled snapshots β live table
import json, os
DB = "prices.json"
current = {}
for item in client.dataset(run["defaultDatasetId"]).iterate_items():
current[item["asin"]] = {
"price": item.get("price"),
"stock": item.get("inStock"),
"stars": item.get("stars"),
}
old = json.load(open(DB)) if os.path.exists(DB) else {}
for asin, p in current.items():
if asin in old and p["price"] and old[asin]["price"]:
drop = (old[asin]["price"] - p["price"]) / old[asin]["price"]
if drop > 0.10:
print(f"PRICE DROP {asin}: {old[asin]['price']} -> {p['price']}")
json.dump(current, open(DB, "w"))
Put the actor on a daily schedule in Apify Console β this script runs via cron/Actions β your comparison pages always show today's price.
Step 4 β Reviews for content angles
junglee/amazon-reviews-scraper with filterByRating: "critical" pulls the worst reviews first β exactly what you need for "pros & cons" sections that readers trust:
curl -X POST "https://api.apify.com/v2/acts/junglee~amazon-reviews-scraper/run-sync-get-dataset-items?token=$APIFY_TOKEN" \
-H "Content-Type: application/json" \
-d '{"productUrls": [{"url": "https://www.amazon.com/dp/B0EXAMPLE"}], "maxReviews": 100, "filterByRating": "critical"}'
Pro tips
-
proxyCountrymust match the marketplace (US β .com, DE β .de) or data comes back wrong/blocked. - Batch ASINs in one run; re-run only failures.
- Pair prices with your Associates tag in the outbound URL β
?tag=yourtag-20.
More tools on awesome-web-scraping. Agent users: npx skills add g4dr/apify-skills β the apify-amazon-products skill does this end-to-end (repo).
What niche are you building a feed for?
Top comments (1)
The part Iβd be careful with is treating the latest scrape as the current truth. Imagine a comparison page tracking 5,000 ASINs across multiple Amazon marketplaces. A crawler can finish successfully while returning stale prices, missing offers, or incomplete stock data for a subset of products. If that snapshot replaces the previous dataset wholesale, a temporary scraping failure can look like thousands of products suddenly disappearing or changing price.
Iβd keep the last-known-good snapshot, validate each batch before publishing it, and track
price_observed_at, marketplace, and scrape status per ASIN. Price-drop alerts should also ignore missing or invalid values instead of treating them as real changes. For production, Iβd evaluate Amazonβs Creators API before building around scraping, especially since PA-API 5.0 was deprecated in May 2026. The APIβs rate limits and eligibility requirements still need to be part of the design, though. A feed that knows when its data is unreliable is much more useful than one that simply refreshes every night.