eBay Scraper: Listings and Sold Prices
ProxyField scrapes eBay with its Web Scraping API: send any eBay search, sold-listings, item or seller URL, on ebay.com, ebay.co.uk or 6 other eBay sites, for $0.50 per 1,000 successful pages over plain HTTP (from $0.20 at volume) or $2.00 with JS rendering (from $1.00). The API returns the page; the parse_results(), parse_item() and parse_seller() functions on this page return the JSON (sample below). You pay per page, not per item: a search page holds up to 60 listings, so 1,000 sold listings take about 17 pages, about $0.0085 over plain HTTP or $0.034 rendered, while 1,000 item pages cost $0.50. Sold data covers recent sales only, where eBay shows them to signed-out visitors, and a multi-quantity listing shows a total sold, not each sale. To start, contact sales, or build your own scraper on residential proxies with the Easy Trial, 1 GB for $2.95.
Through the sales team on our 24/7 live chat
| Fetch | Entry | Volume, from |
|---|---|---|
| HTTP | $0.50 | $0.20 |
| JS rendering | $2.00 | $1.00 |
Billed on successful results only.
| Question | Answer |
|---|---|
| Price | $0.50 per 1,000 successful pages over plain HTTP (from $0.20); $2.00 with JS rendering (from $1.00) |
| What is "one result" | One successful page: a search page with up to 60 listings, or one item page |
| Kind of tool | Page API: the API returns the eBay page, the parser on this page returns the JSON |
| JSON fields | Search pages: item ID, title, price, currency, condition, format, bids, quantity sold, watchers, sold date, shipping, seller, feedback score, positive %. Item pages: also brand, GTIN, item specifics, images, description URL. Seller pages: store name, positive %, items sold, followers |
| Example month | 2,000 sold-listing searches a day = 60,000 pages = $30 a month ($12 at the volume price) |
| Sold listings | A search with LH_Sold=1&LH_Complete=1, same price as any page, where eBay shows the results to signed-out visitors |
| eBay UK and other sites | Yes: an ebay.co.uk URL returns UK listings in GBP; the 8 eBay sites in the table below are each one more URL |
| Failed requests | Not billed: you pay only for successful results |
What the JSON looks like
One card from an ebay.co.uk sold-listings page, https://www.ebay.co.uk/sch/i.html?_nkw=mechanical+keyboard&LH_Sold=1&LH_Complete=1, as parse_results() returns it (example values):
{
"item_id": "226612345678",
"title": "Keychron K2 Wireless Mechanical Keyboard",
"price": 42.0,
"currency": "GBP",
"condition": "Pre-owned",
"format": "buy_it_now",
"bids": null,
"quantity_sold": null,
"watchers": null,
"shipping": "+£4.99 postage",
"sold_date": "14 Oct 2026",
"url": "https://www.ebay.co.uk/itm/226612345678",
"seller": "keyboardshed",
"positive_pct": 99.6,
"feedback_score": 1284
}The same search on ebay.com returns USD, on ebay.de EUR: the site in the URL sets the listings and the currency.
Which eBay scraper tools return clean JSON?
Two kinds of tool return eBay data as JSON. Parsed-field eBay APIs take a keyword or URL and return named fields, billed per item or per request. Page APIs, like ProxyField's Web Scraping API, return the eBay page, billed per page, and a parser turns it into JSON; this page gives you that parser.
Read moreShow less
| Item | Parsed-field eBay API | ProxyField: page API + parser |
|---|---|---|
| You send | A keyword or an eBay URL | Any eBay URL: search, sold listings, item, seller, feedback |
| You get | JSON in the vendor's field names | The page; parse_results() and parse_item() below return the JSON |
| Unit you pay for | Per item or per request | Per page: $0.50 per 1,000 successful results, from $0.20 |
| 1,000 sold listings | 1,000 items | About 17 search pages of 60, under 1 cent |
| When eBay changes its markup | The vendor updates its parser | You update the selectors; the parser matches two card layouts |
| Field names | The vendor's | Yours: change any key in the code |
| Fields per page type | Set by the vendor | Search: 15 fields per listing, watchers included. Item: specifics, brand, GTIN, images, watchers. Seller: store name, positive %, items sold, followers |
Fields to ask of any eBay JSON tool
Check a tool against this list before you buy; the right column is what the parser on this page returns.
| Field | Why you need it | ProxyField parser |
|---|---|---|
| Item ID | De-duplicates rows across runs | item_id, search and item pages |
| Title | Matches listings to your products | title |
| Price and currency | Comps across ebay.com, ebay.co.uk, ebay.de and other sites | price, currency (USD, GBP, EUR, CAD, AUD) |
| Condition | New and used items sell at different prices | condition |
| Format | Auction, Buy It Now or Best Offer prices are not comparable | format |
| Bids | Shows auction demand | bids |
| Quantity sold | Sales volume of a multi-quantity listing | quantity_sold |
| Sold date | Dates a comp | sold_date, on sold-listings pages |
| Shipping | The real price to the buyer | shipping |
| Seller and feedback | Seller checks before you buy wholesale lots | seller, feedback_score, positive_pct; parse_seller() adds store, items_sold, followers |
| Item specifics | Brand, model, size and other attributes | item_specifics, brand, gtin (item pages) |
| Images | Listing photos | images (item pages) |
| Watchers | Interest in an active listing | watchers, search and item pages of active listings |
ProxyField sells no separate eBay API with pre-parsed fields; the parser on this page is the JSON layer. The Web Scraping API itself returns the page as HTML, Markdown or plain text, or a JSON envelope with the status code, the final URL, the headers, the cookies and the content; it has no parsed eBay fields, so your parser reads them.
Turn eBay pages into JSON
The Web Scraping API returns the eBay page; these two functions turn it into JSON. parse_results() reads a search or sold-listings page, one row per listing, in both card layouts eBay uses (li.s-card and the older li.s-item), and skips the "Shop on eBay" ad card. parse_item() reads an item page: its schema.org Product data, when the page carries it, the item specifics, the watcher count and the description frame's URL. parse_seller() reads a seller's store or feedback page: the store name, positive feedback percentage, items sold and followers. The functions match the text eBay shows ("23 watchers", "99.6% positive feedback", "12K items sold"); eBay changes its markup, so check the selectors on a live page before a large run.
Read moreShow less
import json, re
from bs4 import BeautifulSoup
CURRENCY = {"£": "GBP", "$": "USD", "US $": "USD", "AU $": "AUD", "C $": "CAD", "EUR": "EUR", "€": "EUR"}
def money(text):
m = re.search(r"(US \$|AU \$|C \$|EUR|£|€|\$)\s?([\d.,]+)", text or "")
if not m:
return None, None
amount = m.group(2).replace(",", "") if m.group(1) != "EUR" else m.group(2).replace(".", "").replace(",", ".")
return float(amount), CURRENCY[m.group(1)]
def text(card, sel):
el = card.select_one(sel)
return el.get_text(" ", strip=True) if el else None
def parse_results(html):
"""Search and sold-listings pages: one row per listing card."""
soup = BeautifulSoup(html, "html.parser")
rows = []
for card in soup.select("li.s-card, li.s-item"):
link = card.select_one("a[href*='/itm/']")
title = text(card, ".s-card__title, .s-item__title")
item_id = re.search(r"/itm/(\d+)", link["href"]).group(1) if link else None
if not item_id or not title or title == "Shop on eBay": # skip the ad card
continue
price, currency = money(text(card, ".s-card__price, .s-item__price"))
all_text = card.get_text(" | ", strip=True)
sold = re.search(r"Sold\s+([^|]+?)\s*(\||$)", all_text)
ship = re.search(r"(\+?\S+ (delivery|postage|shipping)|Free (delivery|postage|shipping))", all_text)
bids = re.search(r"(\d+) bids?\b", all_text)
qty_sold = re.search(r"([\d,]+)\+? sold\b", all_text)
watchers = re.search(r"([\d,]+)\+? watch(?:ers|ing)\b", all_text)
fmt = "auction" if bids else "best_offer" if "Best Offer" in all_text else "buy_it_now"
seller = re.search(r"(\S+) \(([\d,]+)\) ([\d.]+)%|(\S+) ([\d.]+)% positive \(([\d,]+)\)", all_text)
row = {"item_id": item_id, "title": title, "price": price, "currency": currency,
"condition": text(card, ".s-card__subtitle, .SECONDARY_INFO"),
"format": fmt, "bids": int(bids.group(1)) if bids else None,
"quantity_sold": int(qty_sold.group(1).replace(",", "")) if qty_sold else None,
"watchers": int(watchers.group(1).replace(",", "")) if watchers else None,
"shipping": ship.group(1) if ship else None,
"sold_date": sold.group(1).strip() if sold else None,
"url": link["href"].split("?")[0]}
if seller and seller.group(1):
row.update(seller=seller.group(1), feedback_score=int(seller.group(2).replace(",", "")),
positive_pct=float(seller.group(3)))
elif seller:
row.update(seller=seller.group(4), positive_pct=float(seller.group(5)),
feedback_score=int(seller.group(6).replace(",", "")))
rows.append(row)
return rows
def parse_item(html):
"""Item page: the schema.org Product block, item specifics and the description frame's URL."""
soup = BeautifulSoup(html, "html.parser")
product = {}
for tag in soup.select("script[type='application/ld+json']"):
data = json.loads(tag.string or "{}")
if isinstance(data, dict) and data.get("@type") == "Product":
product = data
break
offer = product.get("offers") or {}
offer = offer[0] if isinstance(offer, list) else offer
specifics = {}
for pair in soup.select(".ux-labels-values"):
label, value = text(pair, ".ux-labels-values__labels"), text(pair, ".ux-labels-values__values")
if label and value:
specifics[label.rstrip(":")] = value
page = soup.get_text(" | ", strip=True)
qty_sold = re.search(r"([\d,]+)\+? sold\b", page)
watchers = re.search(r"([\d,]+)\+? watch(?:ers|ing|ed)\b", page)
frame = soup.select_one("iframe#desc_ifr")
return {"item_id": (re.search(r"/itm/(\d+)", offer.get("url", "")) or [None, None])[1],
"title": product.get("name") or text(soup, "h1"),
"price": float(offer["price"]) if offer.get("price") else None,
"currency": offer.get("priceCurrency"),
"condition": (offer.get("itemCondition") or "").rsplit("/", 1)[-1] or None,
"availability": (offer.get("availability") or "").rsplit("/", 1)[-1] or None,
"quantity_sold": int(qty_sold.group(1).replace(",", "")) if qty_sold else None,
"watchers": int(watchers.group(1).replace(",", "")) if watchers else None,
"brand": (product.get("brand") or {}).get("name"),
"gtin": product.get("gtin13") or product.get("gtin"),
"item_specifics": specifics,
"images": product.get("image") or [],
"description_url": frame["src"] if frame else None}
def count(value):
"""'1.2K' -> 1200, '3,456' -> 3456"""
value = value.replace(",", "")
return int(float(value[:-1]) * 1000) if value.upper().endswith("K") else int(float(value))
def parse_seller(html):
"""Seller's store or feedback page: name, positive %, items sold, followers."""
soup = BeautifulSoup(html, "html.parser")
page = soup.get_text(" | ", strip=True)
positive = re.search(r"([\d.]+)% positive feedback", page)
sold = re.search(r"([\d.,]+K?) items? sold", page, re.I)
followers = re.search(r"([\d.,]+K?) followers?", page, re.I)
return {"store": text(soup, "h1"),
"positive_pct": float(positive.group(1)) if positive else None,
"items_sold": count(sold.group(1)) if sold else None,
"followers": count(followers.group(1)) if followers else None}
# html = the page the Web Scraping API returned, or resp.text from the proxy example below
# print(json.dumps(parse_results(html), indent=2, ensure_ascii=False)) # search or sold-listings page
# print(json.dumps(parse_item(html), indent=2, ensure_ascii=False)) # item page
# print(json.dumps(parse_seller(html), indent=2, ensure_ascii=False)) # seller store or feedback pageOutput of parse_results() for an auction card on a sold-listings page of ebay.com (example values):
{
"item_id": "115998877665",
"title": "Ducky One 2 Mini RGB 60% Keyboard",
"price": 58.99,
"currency": "USD",
"condition": "Used",
"format": "auction",
"bids": 7,
"quantity_sold": null,
"watchers": null,
"shipping": "Free delivery",
"sold_date": "Oct 12, 2026",
"url": "https://www.ebay.com/itm/115998877665",
"seller": "techresale",
"feedback_score": 842,
"positive_pct": 100.0
}Output of parse_item() for an item page (example values):
{
"item_id": "335500011122",
"title": "Logitech MX Keys Wireless Keyboard",
"price": 79.99,
"currency": "USD",
"condition": "NewCondition",
"availability": "InStock",
"quantity_sold": 1204,
"watchers": 37,
"brand": "Logitech",
"gtin": "5099206088962",
"item_specifics": {"Brand": "Logitech", "Connectivity": "Bluetooth", "Layout": "US"},
"images": ["https://i.ebayimg.com/images/g/abc/s-l1600.jpg", "https://i.ebayimg.com/images/g/def/s-l1600.jpg"],
"description_url": "https://itm.ebaydesc.com/itmdesc/335500011122?t=0"
}| eBay page | Fields a public page shows |
|---|---|
| Search and sold-listings results | Item ID, title, price and currency, condition, shipping, Buy It Now or auction, bids, quantity sold, sold date, seller name, feedback score and positive percentage, listing URL, image |
| Item page | The above plus item specifics, quantity available and sold, return policy, all images; the description loads from a separate URL |
| Seller page | Seller name, feedback score, positive feedback percentage, store name, items sold, followers |
| Feedback | Rating, comment text, date, item |
What one result returns, and what 1,000 sold items cost
You pay per page, not per listing, so the cost per sold item depends on how many listings a page holds. 2,000 sold-listing searches a day are 60,000 pages a month: $30 over plain HTTP, $12 at the volume price, for up to 3.6 million sold listings read. An eBay search page shows up to 60 listings by default; eBay's results-per-page setting _ipg can raise that where your eBay site offers a larger page, so check the count on your target site before you plan a budget.
| Page you fetch | Listings per result | Pages for 1,000 listings | 1,000 listings, plain HTTP ($0.50 per 1,000 pages) | 1,000 listings, JS rendering ($2.00 per 1,000 pages) |
|---|---|---|---|---|
| Sold-listings search, default page size | up to 60 | 17 | about $0.0085 | about $0.034 |
Sold-listings search with _ipg=240, where offered | up to 240 | 5 | about $0.0025 | $0.01 |
| Item page (specifics, description, all images) | 1 | 1,000 | $0.50 | $2.00 |
To compare with a per-item price, use the same unit: 1,000 sold listings from 60-listing search pages are 17 results, under 1 cent over plain HTTP and about 3.4 cents rendered, and 1,000 item pages are $0.50. The last page of a search counts as one result even if it lists 5 items, and only successful pages are billed. Fetch item pages only for the items whose specifics you need.
Sold listings and completed sales
A sold-listings search is one more eBay URL: add LH_Sold=1&LH_Complete=1 to the search, and every card shows the price the item sold for and the sold date. The Web Scraping API fetches it at the same price as any other page, because the price depends only on the mode (plain HTTP or JS rendering), not on the page type.
-
Build the URL:
_nkwfor the keyword,LH_Sold=1&LH_Complete=1for sold items,_ipgfor the page size,_pgnfor the page number. -
Fetch page 1, parse it with
parse_results(), then raise_pgnuntil a page returns no rows. -
Keep
item_id,price,currency,formatandsold_datefor each row; skip rows you already have byitem_id. -
Run the same searches daily or weekly to build a longer history.
Limits of sold-listings data:
- Recent sales only. eBay's sold search covers recent sales; the oldest
sold_dateon the last page shows how far back your eBay site goes. - Signed-out access. Collect sold listings only where eBay shows them to signed-out visitors. If a sold search returns a sign-in page instead of listings, stop: data behind a login you are not entitled to is outside ProxyField's acceptable use, and a sign-in page served with a 200 status is still a billed result.
- The card has the sale, not the specifics. Item specifics need the item page, one result each ($0.50 per 1,000).
- Multi-quantity listings show a total
quantity_sold, not a price and date for each sale. - Prices are as shown. Auction, Buy It Now and Best Offer prices sit side by side; filter on
formatbefore you average.
eBay UK and other eBay sites
Yes, a scraper API can collect eBay UK listings: send an ebay.co.uk search or item URL, and the page comes back with UK listings and prices in GBP, at the same $0.50 per 1,000 successful results. eBay's own supported route is its Browse API, which selects eBay UK with the header X-EBAY-C-MARKETPLACE-ID: EBAY_GB; eBay's User Agreement requires its permission for scraping. The Web Scraping API takes any URL, so each eBay site is one more URL; the table lists 8 of them, each with its own domain and currency:
| eBay site | Currency | Sold-listings URL | Browse API marketplace ID |
|---|---|---|---|
| ebay.com | USD | https://www.ebay.com/sch/i.html?_nkw=KEYWORD&LH_Sold=1&LH_Complete=1 | EBAY_US |
| ebay.co.uk | GBP | https://www.ebay.co.uk/sch/i.html?_nkw=KEYWORD&LH_Sold=1&LH_Complete=1 | EBAY_GB |
| ebay.de | EUR | https://www.ebay.de/sch/i.html?_nkw=KEYWORD&LH_Sold=1&LH_Complete=1 | EBAY_DE |
| ebay.fr | EUR | https://www.ebay.fr/sch/i.html?_nkw=KEYWORD&LH_Sold=1&LH_Complete=1 | EBAY_FR |
| ebay.it | EUR | https://www.ebay.it/sch/i.html?_nkw=KEYWORD&LH_Sold=1&LH_Complete=1 | EBAY_IT |
| ebay.es | EUR | https://www.ebay.es/sch/i.html?_nkw=KEYWORD&LH_Sold=1&LH_Complete=1 | EBAY_ES |
| ebay.ca | CAD | https://www.ebay.ca/sch/i.html?_nkw=KEYWORD&LH_Sold=1&LH_Complete=1 | EBAY_CA |
| ebay.com.au | AUD | https://www.ebay.com.au/sch/i.html?_nkw=KEYWORD&LH_Sold=1&LH_Complete=1 | EBAY_AU |
The site decides the listings and the currency; the visitor's location can change shipping costs and which sellers ship to you. Two ways to see ebay.co.uk as a UK shopper:
| Route | How the UK view is set | Cost |
|---|---|---|
| Web Scraping API | The ebay.co.uk URL; country sets the country the request comes from (the exit IP), as a two-letter code such as gb; the countries it accepts: the proxy pool's 195+ countries | $0.50 per 1,000 successful pages |
| Your own scraper on ProxyField residential proxies | A UK residential IP: 16.6M+ IPs in the United Kingdom across 640+ cities, set in the proxy username (-country-gb) | $2.95/GB for 1 GB, from $1.95/GB |
Pricing: $0.50 per 1,000 results, from $0.20
You are billed on successful results only. For availability and access, contact sales through the sales team on our 24/7 live chat. The volume price starts at 10,000 successful results in one purchase.
What a month costs with plain HTTP (30-day month, one page per result):
| Route | Entry price | At volume |
|---|---|---|
| Web Scraping API, plain HTTP | $0.50 per 1,000 successful results | from $0.20 |
| Web Scraping API, JS rendering | $2.00 per 1,000 successful results | from $1.00 |
| Your own scraper on residential proxies | $2.95/GB (Easy Trial: 1 GB) | from $1.95/GB at 1,000+ GB |
| Workload | Pages a month | Sold listings read (up to 60 per page) | At $0.50 | At $0.20 (volume) |
|---|---|---|---|---|
| 2,000 sold-listing searches a day | 60,000 | up to 3,600,000 | $30 | $12 |
| 20,000 item pages a day | 600,000 | 600,000 items | $300 | $120 |
Payment and balance for the API: the same crypto balance as proxies, which never expires; there is no subscription or monthly fee. All prices: pricing.
Through the sales team on our 24/7 live chat
Plain HTTP or JS rendering for eBay
You pay only for successful results, whichever mode you use. eBay search and item pages carry their listings in the HTML, so start with plain HTTP at $0.50 per 1,000 and switch a page type to JS rendering, $2.00 per 1,000, if it comes back as a challenge or error page instead of listings. eBay does refuse some requests: a plain request from a datacenter server without a proxy got eBay's 403 "Error Page" on both ebay.com and ebay.co.uk in our test on 2026-10-25. The seller's description loads in a separate frame, which is one more URL to fetch (description_url in parse_item). The API takes a POST to https://api.proxyfield.io/v1/scrape with your API key in an Authorization: Bearer <api_key> header and a JSON body: url, render (false for plain HTTP, true for JS rendering), country and output (html, markdown, text or json). Parameter reference: API documentation. The API has no scheduler: your code sends the requests when you need them. Asynchronous jobs, batches of URLs and callbacks: jobs and batches of up to 1,000 requests, with a signed callback for each finished job; results are kept for 48 hours. Concurrency and rate limits: 20 concurrent requests per account; higher limits through sales.
# The request the Web Scraping API takes (access through Contact sales)
curl https://api.proxyfield.io/v1/scrape \
-H "Authorization: Bearer <api_key>" \
-H "Content-Type: application/json" \
-d '{"url": "https://www.ebay.co.uk/sch/i.html?_nkw=mechanical+keyboard&LH_Sold=1&LH_Complete=1", "render": false, "country": "gb", "output": "json"}'Example response (shortened; content is the page's HTML, which parse_results() reads):
{
"metadata": {"id": "req_a7d2e05c91f3b468", "api": "web_scrape", "status": "success", "billed": true},
"status_code": 200,
"final_url": "https://www.ebay.co.uk/sch/i.html?_nkw=mechanical+keyboard&LH_Sold=1&LH_Complete=1",
"content_type": "text/html; charset=utf-8",
"content": "<!DOCTYPE html><html lang=\"en-GB\">…</html>"
}eBay's official API or scraping?
eBay's Browse API returns active listings and item details as fields. You pick the eBay site with the X-EBAY-C-MARKETPLACE-ID header (EBAY_GB for ebay.co.uk); eBay lists 16 marketplaces for it, sets a default limit of 5,000 calls a day, and says Buy APIs require an additional license. Its sold-item data is limited to approved partners. If the Browse API covers your fields and volume, use it; scraping reads what any shopper sees on the public pages, including sold listings.
| Item | eBay Browse API | Web Scraping API |
|---|---|---|
| Who can use it | Registered eBay developers with the Buy API license | ProxyField customers |
| Data | Active listings and item details, as fields | Any public eBay page, including sold listings |
| eBay site | X-EBAY-C-MARKETPLACE-ID header, 16 marketplaces | The site's URL |
| Limits | 5,000 calls a day by default | Billed per 1,000 successful results |
| Parsing | Done by eBay | Yours, with the parser on this page |
Sources: eBay's supported marketplaces and Buy API call limits.
Scrape eBay with Python and ProxyField proxies
To scrape eBay yourself, request the search URL through rotating residential proxies, parse it with parse_results() above and page through the results with _pgn. ProxyField gives you a new IP on every request or a sticky session from 30 s to 36 h, over HTTP, HTTPS or SOCKS5, with unlimited concurrent threads.
import json, time
import requests
proxy = "http://<login>-country-us-city-new_york:<password>@gate.proxyfield.io:7000"
rows = []
for page in range(1, 4):
params = {"_nkw": "mechanical keyboard", "LH_Sold": 1, "LH_Complete": 1, "_ipg": 60, "_pgn": page}
resp = requests.get("https://www.ebay.com/sch/i.html", params=params,
proxies={"http": proxy, "https": proxy},
headers={"User-Agent": "Mozilla/5.0", "Accept-Language": "en-US"},
timeout=30)
resp.raise_for_status() # on 403 or 429, slow down instead of retrying at once
batch = parse_results(resp.text) # the function from "Turn eBay pages into JSON"
if not batch:
break
rows += batch
time.sleep(5)
json.dump(rows, open("ebay_sold.json", "w"), indent=2)Access opens once the payment is confirmed; the gateway, credentials or allowlist are in your account. The username format is <login>-country-us-city-new_york; other tokens: -region-<region>, -session-<id> and -ttl-<seconds> (30 to 129,600 seconds, 20 minutes by default) after the location, as in <login>-country-us-region-new_york-city-new_york-session-he9f2qga-ttl-600.
Residential proxies cost $2.95/GB for 1 GB and fall to $1.95/GB from 1,000 GB, with no subscription; the traffic never expires, and all purchases are final. For a browser instead of requests, see Playwright or Puppeteer. Proxy setup for eBay accounts and research: eBay proxies.
What teams use eBay data for
- Sold-price comps for resellers who price used and collectible items.
- Price and listing monitoring of your own and competing sellers.
- Category and demand research: which items sell, at what price, how fast.
- MAP checks on authorized sellers.
- Seller and feedback analysis before you buy wholesale lots.
Collect public pages only; bidding, buying or selling through a scraper is not a data job.
Legal questions
eBay's User Agreement prohibits robots, scrapers and other automated access without eBay's permission, and a scraper API does not give you that permission: check your use against it, ask eBay, or use eBay's API. The details are in Is Scraping E-commerce Sites Legal?. ProxyField's acceptable use policy allows collecting public web data and price monitoring, and forbids accessing data behind logins you are not entitled to. For the wider question, read Is Web Scraping Legal? US, EU and UK Rules (2026). ProxyField's rule for every site: public pages only, and follow the site's terms. This is not legal advice.
More scrapers
- Amazon Scraper API: Amazon product and search pages, $0.60 per 1,000 successful results, from $0.30.
- Walmart scraper, the e-commerce scraper and price scraping: pages for other stores on the same Web Scraping API, not separate APIs.
- Google SERP API: the Google results page as JSON, $1.20 per 1,000 successful results, from $0.80.
- All scrapers: scrapers.
eBay Scraper FAQ
24/7 support by live chat, including help with setup and integration.
How much does an eBay scraper API cost per 1,000 results, and does it cover sold listings?
ProxyField's Web Scraping API costs $0.50 per 1,000 successful results over plain HTTP, from $0.20 at volume, and $2.00 with JS rendering, from $1.00. A result is one page, not one item: 1,000 sold listings from 60-listing search pages are about 17 results, about $0.0085 over plain HTTP or $0.034 rendered, while 1,000 item pages cost $0.50. Sold listings are covered: a sold-listings search costs the same as any page, for recent sales where eBay shows them to signed-out visitors, and failed requests are not billed.
Which eBay scraper tools return listings, prices and seller data as clean JSON?
Two kinds: parsed-field eBay APIs that return named fields and bill per item or request, and page APIs that return the page for a parser, billed per page. ProxyField's Web Scraping API is the second kind, at $0.50 per 1,000 pages, and the three Python functions on this page return the JSON: 15 fields per listing from search pages (item ID, title, price, currency, condition, format, bids, quantity sold, watchers, sold date, shipping, seller, feedback score, positive %, URL), plus brand, GTIN, item specifics and images from item pages, and store name, items sold and followers from seller pages.
Can I scrape listings from a specific country's eBay site, like eBay UK, with a scraper API?
Yes: an ebay.co.uk URL returns UK listings with prices in GBP, at the same $0.50 per 1,000 successful results, and ebay.de, ebay.fr, ebay.it, ebay.es, ebay.ca and ebay.com.au work the same way. For a UK shopper's view on your own scraper, ProxyField has 16.6M+ residential IPs in the United Kingdom; eBay's own Browse API selects eBay UK with the marketplace ID EBAY_GB. eBay's User Agreement still requires its permission for automated access.
What fields should an eBay scraper return as JSON?
At least item ID, title, price and currency, condition, format (auction, Buy It Now or Best Offer), bids, quantity sold, sold date, shipping, and seller with feedback score; item specifics and images come from item pages. The parser on this page returns all of these, plus watchers on active listings.
Can I scrape eBay sold listings without signing in?
Only where eBay shows sold listings to signed-out visitors: a search with LH_Sold=1&LH_Complete=1 then lists sold prices and dates, at $0.50 per 1,000 pages. If eBay answers with a sign-in page instead, stop, because data behind a login you are not entitled to is outside ProxyField's acceptable use.
How many listings does one eBay results page hold?
60 by default; eBay's _ipg setting also offers 120 and 240 per page. With the Web Scraping API the whole page is one result, so a larger page size lowers the cost per listing.
What is an eBay scraper?
A tool or API that collects public data from eBay pages, such as listing titles, prices, sold prices, shipping and seller feedback. It either returns the page for your own parser or returns parsed fields.
How do I scrape eBay?
Send eBay search or item URLs to the Web Scraping API and parse the pages it returns, or run your own Python scraper on rotating residential proxies, as in the code on this page. Either way, collect public pages only and keep the request rate low.
How do I scrape eBay listings?
Build a search URL with _nkw for the keyword, _ipg for the page size and _pgn for the page, fetch each results page and read the item ID, title, price, condition and shipping from every card. Fetch the item page when you need item specifics or the description.
How do I scrape eBay sold listings?
Add LH_Sold=1&LH_Complete=1 to the search URL: every card then shows what the item sold for and when. eBay shows recent sales only, so run the search on a schedule and de-duplicate by item ID to build a longer history.
Show 16 more questionsShow fewer questions
What data can you scrape from eBay?
Public eBay pages show listing titles, prices, condition, shipping, bids, item specifics, sold prices and dates, and seller names with feedback scores. The table on this page lists them by page type.
What is the best eBay scraper?
ProxyField's Web Scraping API fetches any eBay page, sold listings included, for $0.50 per 1,000 successful results, or you build your own scraper on its residential proxies from $1.95/GB. When you compare tools, check the eBay sites covered, whether you pay per page or per item, whether failed requests are billed and who does the parsing.
How do I scrape eBay with Python?
Request the search URL with requests through a residential proxy, parse the cards with Beautiful Soup and page through with _pgn, as in the code on this page. eBay changes its markup, so check the selectors before each run.
Do I need proxies to scrape eBay?
For more than a few pages, yes: eBay limits requests per IP, and a plain request from a datacenter server got eBay's 403 error page in our test on 2026-10-25. Spread a modest job over rotating residential IPs and pace it. With the Web Scraping API you send URLs and the API does the fetching.
Can I scrape eBay seller data?
Yes, from public pages: a seller's store or feedback page shows the store name, positive feedback percentage, items sold and followers, and parse_seller() on this page returns them as JSON. Each seller page is one result, $0.50 per 1,000 over plain HTTP; search cards already carry the seller name, feedback score and positive %.
How do I scrape eBay reviews?
Seller feedback and product reviews sit on their own pages, and each is one more URL to fetch. Parse the rating, comment, date and item from each entry, and collect public feedback only.
Does eBay have an official API?
Yes: the Browse API returns active listings and item details to registered developers with the Buy API license, with a default limit of 5,000 calls a day. eBay's sold-item data is limited to approved partners, which is why sold prices are often read from the public sold-listings pages.
Does eBay block web scraping?
eBay limits automated requests and can block an IP that sends too many, usually with a 403 or 429 answer. Keep the rate low, slow down on those answers and collect public pages only; with the Web Scraping API, you pay only for successful results.
Do you need a headless browser to scrape eBay?
Not for the data: search and item pages carry their listings in the HTML, so start with plain HTTP at $0.50 per 1,000 results. Switch a page type to JS rendering, at $2.00 per 1,000, if it returns a challenge or error page instead of listings.
Why do businesses scrape eBay data?
To see real sold prices, track competing listings, research demand in a category and check sellers before they buy from them. eBay's sold listings are one of the few public records of what used and collectible items actually sell for.
How do I keep an eBay scraper working when the page layout changes?
Match on more than one selector, as the parser on this page does for both card layouts, log the pages where no cards were found, and re-check the markup when that count rises. A test run on a few known URLs before each large job catches most layout changes.
How do I scrape eBay item descriptions that load in an iframe?
The seller's description loads from a separate URL inside the item page. Read that frame's address from the item page and fetch it as one more page.
Can I schedule recurring eBay scraping jobs?
Yes, from your side: run your script or your API requests on a schedule with cron or any job runner. A daily or weekly run of the same sold-listings searches, de-duplicated by item ID, builds a longer price history.
Is there a free eBay scraper?
Open-source scraper code costs nothing, but at any scale you pay for IPs. The smallest ProxyField purchase is the Easy Trial: 1 GB of residential traffic for $2.95, with no minimum purchase and no subscription.
How do I get started with an eBay scraper API?
Contact sales with the eBay sites, page types and volume you plan: the Web Scraping API costs $0.50 per 1,000 successful results over plain HTTP, from $0.20 at volume. To build your own scraper instead, start with the Easy Trial: 1 GB of residential traffic for $2.95.
Related pages
Collect eBay pages with the Web Scraping API
Billed on successful results only. Contact sales for the Web Scraping API and the volume you need, or run your own scraper on residential proxies. 24/7 live chat helps with setup and integration.