Regional Preferences

Language

Nothing in the list matches what you typed there.

Scraping basics · 2026-06-13 · Updated

Track Amazon prices with Python: a small, polite scraper

Follow the price, rating and stock of a few Amazon products with a short Python script, explained line by line, plus when Amazon's official API fits better.

In plain English: this script opens an Amazon product page and reads five things from it: the title, the price, the star rating, the number of reviews and whether the item is in stock. That's handy if you're waiting for something you want to buy to drop in price, or if you sell a few items and want to keep an eye on similar products. Amazon is one of the stricter sites about automated visits, though, so most of the work here is about going slowly and politely. Reading the page is the easy part. You'll use Python with requests to fetch pages and beautifulsoup4 to read them, and a proxy so the visits don't all come from your own IP address.

Quick start in 3 steps

  1. Run the pip command from Step 1 to install everything.
  2. Paste your proxy host, port and login into the dictionary in Step 2.
  3. Run the script for one product code and check that a title and a price print out.

Is this allowed? The ground rules

Stick to product information that any visitor can see. Leave anything behind a login alone, along with personal details about the people who buy and sell there. Read Amazon's robots.txt (the file where a site tells automated programs what to leave alone) and its Terms of Service, and keep within them. When you need catalogue data on a larger scale, Amazon has official APIs for that, such as the Product Advertising API, and they're the proper, approved route. Don't try to beat a CAPTCHA or a sign-in page, keep your request rate low, and treat this script as a tool for light personal research, not for copying the catalogue. Making sure your use is permitted is your responsibility.

Which proxy type works on Amazon?

Amazon pays close attention to how many pages each IP address asks for, and it's quick to show a CAPTCHA or block an address that asks for too many too fast. Spreading your requests over several addresses keeps each one's share small. Amazon is especially wary of address ranges that belong to data centres, so residential proxies, which use household broadband addresses, are the dependable choice for product pages. If you still run into trouble on certain pages, residential premium gives you a little more room. Checking prices in another country's store? Use proxies in that country. Our proxy for scraping page explains how to match the proxy type to the job.

What you need

  • Python 3, already installed, and a window for typing commands.
  • The four proxy details: host, port, username and password.
  • The product codes you want to follow. Amazon calls them ASINs, and Step 3 shows where to find one.

Step 1: Install the libraries

Type this into your terminal. Besides the two main libraries it installs lxml, a quick HTML reader that BeautifulSoup can use behind the scenes:

pip install requests beautifulsoup4 lxml

Step 2: Add your proxy details

Our proxies use the standard HOST:PORT layout with a username and password. Give them to requests as a dictionary, replacing the words in capitals with your own details:

proxies = {
    "http":  "http://USER:PASS@HOST:PORT",
    "https": "http://USER:PASS@HOST:PORT",
}

Step 3: Fetch a product page

Every Amazon product has an ASIN, a short code that appears in the page address as /dp/ASIN. The function below builds that address from the code, fetches the page through the proxy and returns its HTML:

import requests
from bs4 import BeautifulSoup

proxies = {
    "http":  "http://USER:PASS@HOST:PORT",
    "https": "http://USER:PASS@HOST:PORT",
}

headers = {
    "User-Agent": (
        "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) "
        "AppleWebKit/537.36 (KHTML, like Gecko) "
        "Chrome/120.0 Safari/537.36"
    ),
    "Accept-Language": "en-US,en;q=0.9",
    "Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8",
}

def fetch_product(asin, domain="www.amazon.com"):
    url = f"https://{domain}/dp/{asin}"
    resp = requests.get(url, headers=headers, proxies=proxies, timeout=25)
    resp.raise_for_status()
    return resp.text

The headers tell Amazon what kind of browser is asking and which languages and page formats it accepts. timeout=25 stops the script waiting more than 25 seconds for an answer. The domain setting lets you point the same function at a different country's Amazon store later on.

Step 4: Read the five fields

Amazon's page layout varies between product categories and changes often. So for each field, the reader below tries a few known element names in turn and moves on quietly when one is missing. Write your own code the same way, assuming any single selector could come back empty:

def parse_product(html):
    soup = BeautifulSoup(html, "lxml")

    def first_text(*selectors):
        for sel in selectors:
            el = soup.select_one(sel)
            if el and el.get_text(strip=True):
                return el.get_text(strip=True)
        return None

    title = first_text("#productTitle")
    price = first_text(
        "span.a-price span.a-offscreen",
        "#priceblock_ourprice",
        "#priceblock_dealprice",
    )
    rating = first_text("span.a-icon-alt")
    review_count = first_text("#acrCustomerReviewText")
    availability = first_text("#availability span")

    return {
        "title": title,
        "price": price,
        "rating": rating,
        "review_count": review_count,
        "availability": availability,
    }

html = fetch_product("B08N5WRWNW")
print(parse_product(html))

When every field comes back as None (Python's word for "nothing here"), you've most likely been shown a robot-check page or a CAPTCHA instead of the product. Print the HTML and read it before you touch the selectors. The fix is nearly always to slow down and ask for fewer pages, not to rewrite the reader.

Step 5: Follow several products, slowly

For more than a couple of products, loop through them, take turns between proxy endpoints and pause for a random 4 to 10 seconds after each page:

import random
import time

PROXY_POOL = [
    "http://USER:PASS@HOST1:PORT",
    "http://USER:PASS@HOST2:PORT",
    "http://USER:PASS@HOST3:PORT",
]

def scrape_many(asins):
    out = {}
    for asin in asins:
        p = random.choice(PROXY_POOL)
        prox = {"http": p, "https": p}
        try:
            url = f"https://www.amazon.com/dp/{asin}"
            resp = requests.get(url, headers=headers, proxies=prox, timeout=25)
            resp.raise_for_status()
            out[asin] = parse_product(resp.text)
        except requests.RequestException as e:
            out[asin] = {"error": str(e)}
        time.sleep(random.uniform(4, 10))  # be a good citizen
    return out

If one product fails, the error is written down against that product and the loop moves on, so a single bad page can't stop the whole run. If your plan already changes the address on every request, one endpoint is enough, because the switching happens on our side. Whatever your plan, leave the random sleep in place. It's the politeness rule you don't get to skip.

Step 6: Save results and don't fetch twice

There's no need to fetch a page you already have. For price watching, save each result with the time it was collected and refresh on a schedule that suits you. Once a day is plenty for most people. Fewer visits are kinder to Amazon, and fewer visits also mean fewer blocks. This helper adds one line per check to a file called prices.jsonl, where each line is a small, self-contained record:

import json
from datetime import datetime

def save_snapshot(asin, data, path="prices.jsonl"):
    record = {"asin": asin, "fetched_at": datetime.utcnow().isoformat(), **data}
    with open(path, "a", encoding="utf-8") as f:
        f.write(json.dumps(record) + "\n")

Check before you run it

Confirm that your requests leave through the proxy: our my IP tool shows your own address, so you know what you're comparing against, and the proxy checker tests each endpoint in your list. It takes a couple of minutes and spares you a run that quietly used your home connection.

Common mistakes

  • Checking prices every few minutes. Prices rarely change that fast, and frequent visits are what get addresses blocked. Daily is fine.
  • Treating a robot-check page as a broken script. All-empty fields usually mean you went too fast, not that the code is wrong.
  • Comparing different stores without noticing. Each country's Amazon store has its own prices and currency, so keep the domain and the proxy country matched.
  • Deleting the pause "just for a test". Tests count as visits too.

Beginner questions

Where exactly do I find an ASIN?

Open the product in your browser and look at the address bar. The code comes right after /dp/ in the address. Copy that code into the script.

Can the script tell me when a price drops?

Not on its own, but the saved file makes it possible. Each line holds a product code, a time and a price, so a few extra lines of code can compare the newest price with the previous one for the same product.

Why is the price different from the one I see in my browser?

Your browser may be signed in, set to another delivery address or currency, or showing a deal tied to your account. The script sees the page as a visitor in the proxy's country does.

A good Amazon scraper is a patient one. It asks slowly, saves what it finds and reads pages carefully. Stay with public product pages, follow Amazon's terms, and move to the official Product Advertising API if your project outgrows light personal research.

Keep reading

Ready to try one yourself?

Start small: buy a little data in the type that suits your task, check it with our free tools, and top up only if you need more. There’s no contract and no minimum spend.

View our proxies

New to proxies? Start with a small order

Datacenter proxies cost $2.49 per gigabyte (GB) of data you use, so trying one on the site you care about needn’t cost much. Your login details are ready within seconds, and if you get stuck, a real person answers questions 24/7.

Budget Proxies logo

or
Continue with Email

Continue and you're agreeing to our Terms and Privacy Policy.

Already set up with us?

First time with us?

🎉 Money-off code

Knock 10% off
your next order

Type your email below and we’ll send the code over. It works on any proxy plan, however small the order. At checkout, paste it into the Promo code box and press Apply.

You’ll get the code and, now and then, an offer by email. Changed your mind later? Ask us and we’ll take you off the list.

Sorted! It’s on its way 📬

Your 10% code is heading to your inbox. No need to wait for the email, though: copy it from here and paste it in when you check out.

See residential plans →