# Best Buy Product Scraper (`datascrapers/best-buy-scraper`) Actor

Scrape Best Buy products by search query, category URL, or SKU. Optional full details with description, features, specifications, and sample reviews.

- **URL**: https://apify.com/datascrapers/best-buy-scraper.md
- **Developed by:** [Farhan Ali](https://apify.com/datascrapers) (community)
- **Categories:** E-commerce, Integrations, MCP servers
- **Stats:** 1 total users, 0 monthly users, 0.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $2.70 / 1,000 product scrapeds

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.
Since this Actor supports Apify Store discounts, the price gets lower the higher subscription plan you have.

Learn more: https://docs.apify.com/platform/actors/running/actors-in-store#pay-per-event

## What's an Apify Actor?

Actors are web data automations that power AI and operations. They run on the Apify platform to scrape websites, process data, connect APIs, and automate workflows.
In Batch mode, an Actor accepts a well-defined JSON input, performs an action which can take anything from a few seconds to a few hours,
and optionally produces a well-defined JSON output, datasets with results, or files in key-value store.
In Standby mode, an Actor provides a web server which can be used as a website, API, or an MCP server.
Actors are written with capital "A".

## How to integrate an Actor?

If asked about integration, you help developers integrate Actors into their projects.
You adapt to their stack and deliver integrations that are safe, well-documented, and production-ready.
The best way to integrate Actors is as follows.

- **AI agents and MCP clients** — the [Apify MCP server](https://docs.apify.com/integrations/mcp.md) at `https://mcp.apify.com` (remote, streamable HTTP, OAuth on first use).
- **Agentic workflows and local Actor development** — [Agent Skills](https://apify.com/.well-known/agent-skills/index.json) with the [Apify CLI](https://docs.apify.com/cli/docs.md): `npm install -g apify-cli`, then `apify login`.
- **JavaScript/TypeScript projects** — the official [JS/TS client](https://docs.apify.com/api/client/js/docs.md): `npm install apify-client`.
- **Python projects** — the official [Python client](https://docs.apify.com/api/client/python/docs.md): `pip install apify-client`.
- **Any other language** — the [REST API](https://docs.apify.com/api/v2.md).

For usage examples, see the [API](#api) section below.

For more details, see Apify documentation as [Markdown index](https://docs.apify.com/llms.txt) and [Markdown full-text](https://docs.apify.com/llms-full.txt).

# README

**Best Buy Product Scraper** creates a structured dataset of product records collected from Best Buy (bestbuy.com and bestbuy.ca). Each dataset item can include the SKU, title, brand, price and regular price, currency, rating, availability, model number, and product URL. When product details are enabled, records are enriched with description, features, specifications, gallery images, and sample reviews. Query the source with `searchQueries`, `startUrls`, or `skuIds`, control the result limit with `maxItems`, and retrieve records through the Apify Dataset API or export them as JSON, CSV, Excel, XML, or another supported format.

### Dataset at a glance

| Property | Value |
|---|---|
| Source | Best Buy (bestbuy.com, bestbuy.ca) |
| Record unit | One product |
| Input methods | `searchQueries`, `startUrls`, `skuIds` |
| Main identifiers | `skuId`, `bsin`, `url` |
| Delivery | Apify Dataset and API |
| Export formats | JSON, CSV, Excel, XML, HTML |
| Update model | Fresh records per Actor run |
| Pricing | $3.00 per 1,000 products; $4.00 per 1,000 additional for full product details |

### Coverage and available records

The Actor collects product records from Best Buy search, category, and product pages. Supported behavior:

- **Search queries** — `searchQueries` accepts terms like `"laptop"` or `"airpods"`, resolved against the selected market.
- **Start URLs** — `startUrls` accepts category, search, or product URLs; the country is inferred from the host.
- **Direct SKUs** — `skuIds` scrapes specific products by Best Buy SKU.
- **Market selection** — `countryCode` selects `US` (bestbuy.com) or `CA` (bestbuy.ca) for query-based input.
- **Availability context** — `zipCode` and optional `storeId` provide pricing/availability context for the destination area.
- **Listing-only vs. details** — `fetchProductDetails` (default `false`) returns listing/card fields only; when enabled, each product is enriched with description, features, specifications, gallery images, and sample reviews, adding the `product-details` charge event.
- **Result limit** — `maxItems` caps total products (0 = unlimited).

Not currently collected: full review history (only a sample of reviews per product), seller inventory beyond Best Buy, and order/stock history over time.

### Data dictionary

Listing fields (always present when available):

| Field | Type | Nullable | Description | Example |
|---|---:|---|---|---|
| `skuId` | string | no | Best Buy SKU; recommended deduplication key | `12349296` |
| `bsin` | string | yes | Best Buy internal item identifier | `...` |
| `title` | string | no | Product title | `HP - 14" Laptop - Intel N150...` |
| `brand` | string | yes | Brand name | `HP` |
| `modelNumber` | string | yes | Manufacturer model number | `...` |
| `url` | string | yes | Product page URL | `https://www.bestbuy.com/...` |
| `image` | string | yes | Primary image URL | `https://pisces.bbystatic.com/...jpg` |
| `price` | number | yes | Current sale price | `249.0` |
| `regularPrice` | number | yes | Regular/list price | `299.0` |
| `currency` | string | yes | Currency code | `USD` |
| `priceMessage` | string | yes | Display price message | `...` |
| `savings` | number | yes | Absolute savings | `50.0` |
| `savingsPercent` | number | yes | Savings percentage | `17` |
| `ratingAverage` | number | yes | Average rating | `4.5` |
| `ratingCount` | integer | yes | Number of ratings | `1200` |
| `condition` | string | yes | Product condition | `New` |
| `availability` | string | yes | Display availability status | `In Stock` |
| `sellerId` / `sellerClassification` | string | yes | Seller identifiers | `...` |
| `badges` | array | yes | Promotional badge labels | `["Top Rated"]` |
| `countryCode` | string | yes | Market code | `US` |
| `sourceQuery` | string | yes | Query or source used | `laptop` |
| `detailsFetched` | boolean | no | Whether detail enrichment succeeded | `false` |
| `scrapedAt` | string | yes | ISO timestamp | `2026-07-27T10:03:14.296336+00:00` |

Detail fields (present when `fetchProductDetails` is enabled and the page yields them):

| Field | Type | Nullable | Description | Example |
|---|---:|---|---|---|
| `description` | string | yes | Long or short product description | `...` |
| `features` | array | yes | Feature objects with `title` and `description` | `[{"title":"...","description":"..."}]` |
| `specifications` | array | yes | Spec objects with `group`, `name`, `value`, `definition` | `[{"group":"Display","name":"Size","value":"14\""}]` |
| `images` | array | yes | Gallery image URLs | `["https://...jpg"]` |
| `color` | string | yes | Color display name | `Natural Silver` |
| `includedItems` | array | yes | Items included in the box | `["Power adapter"]` |
| `whatItIs` | string | yes | Short product blurb | `...` |
| `disclaimers` | array | yes | Product disclaimers | `[...]` |
| `manuals` | array | yes | Manual objects with `url`, `type`, `language` | `[{"url":"...","type":"Manual"}]` |
| `dimension` | object | yes | `depth`, `height`, `width`, `weight` | `{"weight":"2.0 lb"}` |
| `sampleReviews` | array | yes | Review objects with `rating`, `title`, `text`, `userNickname` | `[{"rating":5,"text":"..."}]` |

### Example dataset record

```json
{
  "skuId": "12349296",
  "title": "HP - 14\" Laptop - Intel N150 Processor - 4GB Memory - 128GB UFS - Natural Silver",
  "image": "https://pisces.bbystatic.com/image2/BestBuy_US/images/products/3bd638b3-4542-4115-8e43-34faa18a2382.jpg;maxHeight=256;maxWidth=384?format=webp",
  "price": 249.0,
  "currency": "USD",
  "countryCode": "US",
  "sourceQuery": "laptop",
  "detailsFetched": false,
  "scrapedAt": "2026-07-27T10:03:14.296336+00:00"
}
```

The record above was produced by a run with `searchQueries: ["laptop"]`, `countryCode: "US"`, and `fetchProductDetails: false`.

### Query and input reference

| Input | Type | Required | Default | Accepted values | Description |
|---|---:|---|---|---|---|
| `searchQueries` | array | no | `["laptop"]` | product terms | Search terms against the selected market |
| `startUrls` | array | no | — | category/search/product URLs | Country inferred from host |
| `skuIds` | array | no | — | Best Buy SKU IDs | Scrape specific products directly |
| `fetchProductDetails` | boolean | no | `false` | `true` / `false` | Enrich with details; adds `product-details` event |
| `countryCode` | string | no | `US` | `US`, `CA` | Market for query-based input |
| `zipCode` | string | no | `55423` | US ZIP or CA postal | Pricing/availability context |
| `storeId` | string | no | `""` | store id | Preferred store for pickup context |
| `maxItems` | integer | no | `0` | 0 = unlimited | Maximum products to scrape |
| `proxyConfiguration` | object | no | residential proxy | proxy settings | Residential proxies are recommended |

Minimal request:

```json
{
  "searchQueries": ["laptop"],
  "countryCode": "US",
  "maxItems": 25,
  "proxyConfiguration": {
    "useApifyProxy": true,
    "apifyProxyGroups": ["RESIDENTIAL"]
  }
}
```

Advanced request (details enrichment):

```json
{
  "startUrls": [
    {
      "url": "https://www.bestbuy.com/site/all-electronics-on-sale/all-apple-on-sale/pcmcat1688758488330.c?id=pcmcat1688758488330"
    }
  ],
  "fetchProductDetails": true,
  "countryCode": "US",
  "zipCode": "55423",
  "maxItems": 5,
  "proxyConfiguration": {
    "useApifyProxy": true,
    "apifyProxyGroups": ["RESIDENTIAL"]
  }
}
```

### Retrieve the data through the API

1. Start the Actor with a JSON input (see above).
2. Wait for the run to finish.
3. Retrieve items from the run's default dataset.
4. Paginate or export the dataset.

Python example:

```python
import json
import urllib.request

API_TOKEN = "<your Apify API token>"
ACTOR_ID = "datascrapers/best-buy-scraper"

payload = {
    "searchQueries": ["laptop"],
    "countryCode": "US",
    "maxItems": 25,
    "proxyConfiguration": {"useApifyProxy": True, "apifyProxyGroups": ["RESIDENTIAL"]},
}

req = urllib.request.Request(
    f"https://api.apify.com/v2/acts/{ACTOR_ID}/runs?token={API_TOKEN}",
    data=json.dumps(payload).encode(),
    headers={"Content-Type": "application/json"},
)
with urllib.request.urlopen(req) as resp:
    run = json.loads(resp.read())["data"]

dataset_id = run["defaultDatasetId"]
with urllib.request.urlopen(
    f"https://api.apify.com/v2/datasets/{dataset_id}/items?token={API_TOKEN}"
) as resp:
    items = json.loads(resp.read())
```

For other languages, use the generated API tab on the Actor's page.

### Data quality and record handling

- **Conditional fields** — detail fields (description, features, specifications, images, reviews) appear only when `fetchProductDetails` is enabled and Best Buy exposes them.
- **Nullable values** — `ratingAverage`, `ratingCount`, and `regularPrice` may be absent for some products.
- **Deduplication** — `skuId` is the stable, recommended unique key. `bsin` and `url` are also unique.
- **Retries and errors** — requests are retried; a product that fails to load is skipped rather than partially written.
- **Normalization** — `price` and `regularPrice` are numeric; `currency` is a separate field, so prices are already machine-readable.

The Actor reflects Best Buy's catalog at run time and does not provide price history.

### Export and pipeline examples

| Destination | Recommended method | Typical use |
|---|---|---|
| PostgreSQL/Supabase | Dataset API or webhook consumer | Product catalog keyed by `skuId` |
| Google Sheets | Apify integration | Review a small result set |
| S3/cloud storage | Scheduled export or integration | Daily price/availability snapshots |
| BI tools | CSV/JSON export | Price and rating trend analysis |

### Pricing and cost examples

The Actor uses pay-per-event billing. Two charge events apply:

- **`dataset-item`** — $3.00 per 1,000 product records returned.
- **`product-details`** — $4.00 per 1,000 products when `fetchProductDetails` is enabled (in addition to the listing event).

Apify plan discounts (Bronze/Silver/Gold) reduce these rates.

| Records | Estimated base cost |
|---:|---:|
| 1,000 products | $3.00 |
| 10,000 products | $30.00 |
| 10,000 products + details | $70.00 |

Estimates assume the free-tier rate and no proxy markup; actual cost depends on your Apify plan and selected options.

### Limitations and responsible data use

- The Actor collects publicly accessible product data only; it does not bypass login or paywalls.
- Results depend on Best Buy's current page structure; site changes can require Actor updates.
- Some fields are conditional or nullable (see Data dictionary).
- The Actor returns a sample of reviews per product, not the full review history.
- The Actor does not retain historical snapshots unless you store them yourself.
- You are responsible for complying with Best Buy's terms of service and applicable privacy and contractual obligations.

### Dataset questions

#### What does one dataset item represent?

One Best Buy product, optionally enriched with full product-page details.

#### Which field should I use as a unique identifier?

`skuId`. `bsin` and `url` are also unique per product.

#### Are fields nullable or conditional?

Yes. Rating and regular price may be null. Detail fields appear only when `fetchProductDetails` is enabled.

#### Can I retrieve the records as CSV or JSON?

Yes. The default dataset supports JSON, CSV, Excel, and XML exports, and the Dataset API returns JSON.

#### How do I paginate large datasets?

Set `maxItems` to bound the run, or paginate the default dataset via the Dataset API.

#### What counts as a billable result?

Each product returned counts as one `dataset-item`. Enabling `fetchProductDetails` adds one `product-details` event per product.

### Related datasets from Data Scrapers

- **[Amazon Search Scraper](https://apify.com/datascrapers/amazon-scraper)** — Amazon product records for cross-retailer price comparison.
- **[HomeDepot Scraper](https://apify.com/datascrapers/homedepot-scraper)** — home-improvement product data with stock levels.
- **[Clutch.co Company Scraper](https://apify.com/datascrapers/clutch-scraper)** — company ratings for joining with product brands and manufacturers.
- **[LinkedIn Company Scraper](https://apify.com/datascrapers/linkedin-company-scraper)** — company records for vendor and brand analysis.

### Data Scrapers support

Need an additional field, record type, or export workflow? Contact Data Scrapers at stardustspotlight@gmail.com. Include a sample source URL, required fields, expected record volume, and preferred delivery format.

# Actor input Schema

## `searchQueries` (type: `array`):

Product search terms (e.g. "laptop", "airpods"). Uses the selected country shop. Provide searchQueries and/or startUrls and/or skuIds.

## `startUrls` (type: `array`):

Best Buy category, search, or product URLs (e.g. https://www.bestbuy.com/site/all-electronics-on-sale/all-apple-on-sale/pcmcat1688758488330.c?id=pcmcat1688758488330). Country is inferred from the host when possible.

## `skuIds` (type: `array`):

Best Buy SKU IDs to scrape directly (optional).

## `fetchProductDetails` (type: `boolean`):

When enabled, loads full product-page details (description, features, specifications, gallery images, sample reviews) and charges the product-details event. When disabled, returns listing/card fields only (faster).

## `countryCode` (type: `string`):

Best Buy market used for searchQueries and bare SKU/category ids when no start URL sets the host. Ignored for startUrls (host wins).

## `zipCode` (type: `string`):

Destination ZIP/postal code used for pricing and availability context (US ZIP or Canadian postal).

## `storeId` (type: `string`):

Optional preferred Best Buy store location id for pickup/availability context.

## `maxItems` (type: `integer`):

Maximum number of products to scrape (0 = unlimited)

## `proxyConfiguration` (type: `object`):

Proxy settings for anti-bot protection. Residential proxies are recommended.

## Actor input object example

```json
{
  "searchQueries": [
    "laptop"
  ],
  "startUrls": [
    {
      "url": "https://www.bestbuy.com/site/all-electronics-on-sale/all-apple-on-sale/pcmcat1688758488330.c?id=pcmcat1688758488330"
    }
  ],
  "fetchProductDetails": false,
  "countryCode": "US",
  "zipCode": "55423",
  "storeId": "",
  "maxItems": 25,
  "proxyConfiguration": {
    "useApifyProxy": true,
    "apifyProxyGroups": [
      "RESIDENTIAL"
    ]
  }
}
```

# Actor output Schema

## `results` (type: `string`):

Dataset containing scraped Best Buy products

## `runStats` (type: `string`):

Aggregate scrape statistics for this run

# API

You can run this Actor programmatically using our API. Below are code examples in JavaScript, Python, and CLI, as well as the OpenAPI specification and MCP server setup.

## JavaScript example

```javascript
import { ApifyClient } from 'apify-client';

// Initialize the ApifyClient with your Apify API token
// Replace the '<YOUR_API_TOKEN>' with your token
const client = new ApifyClient({
    token: '<YOUR_API_TOKEN>',
});

// Prepare Actor input
const input = {
    "searchQueries": [
        "laptop"
    ],
    "startUrls": [
        {
            "url": "https://www.bestbuy.com/site/all-electronics-on-sale/all-apple-on-sale/pcmcat1688758488330.c?id=pcmcat1688758488330"
        }
    ],
    "zipCode": "55423",
    "maxItems": 25,
    "proxyConfiguration": {
        "useApifyProxy": true,
        "apifyProxyGroups": [
            "RESIDENTIAL"
        ]
    }
};

// Run the Actor and wait for it to finish
const run = await client.actor("datascrapers/best-buy-scraper").call(input);

// Fetch and print Actor results from the run's dataset (if any)
console.log('Results from dataset');
console.log(`💾 Check your data here: https://console.apify.com/storage/datasets/${run.defaultDatasetId}`);
const { items } = await client.dataset(run.defaultDatasetId).listItems();
items.forEach((item) => {
    console.dir(item);
});

// 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/js/docs

```

## Python example

```python
from apify_client import ApifyClient

# Initialize the ApifyClient with your Apify API token
# Replace '<YOUR_API_TOKEN>' with your token.
client = ApifyClient("<YOUR_API_TOKEN>")

# Prepare the Actor input
run_input = {
    "searchQueries": ["laptop"],
    "startUrls": [{ "url": "https://www.bestbuy.com/site/all-electronics-on-sale/all-apple-on-sale/pcmcat1688758488330.c?id=pcmcat1688758488330" }],
    "zipCode": "55423",
    "maxItems": 25,
    "proxyConfiguration": {
        "useApifyProxy": True,
        "apifyProxyGroups": ["RESIDENTIAL"],
    },
}

# Run the Actor and wait for it to finish
run = client.actor("datascrapers/best-buy-scraper").call(run_input=run_input)

# Fetch and print Actor results from the run's dataset (if there are any)
print(f"💾 Check your data here: https://console.apify.com/storage/datasets/{run.default_dataset_id}")
for item in client.dataset(run.default_dataset_id).iterate_items():
    print(item)

# 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/python/docs/quick-start

```

## CLI example

```bash
echo '{
  "searchQueries": [
    "laptop"
  ],
  "startUrls": [
    {
      "url": "https://www.bestbuy.com/site/all-electronics-on-sale/all-apple-on-sale/pcmcat1688758488330.c?id=pcmcat1688758488330"
    }
  ],
  "zipCode": "55423",
  "maxItems": 25,
  "proxyConfiguration": {
    "useApifyProxy": true,
    "apifyProxyGroups": [
      "RESIDENTIAL"
    ]
  }
}' |
apify call datascrapers/best-buy-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,datascrapers/best-buy-scraper"
        }
    }
}

```

The hosted server signs you in with OAuth on first connect, so no API token belongs in this config. Clients without OAuth support can send an `Authorization: Bearer <APIFY_API_TOKEN>` header instead, using a token from API & Integrations in Apify Console (https://console.apify.com/settings/integrations).

## OpenAPI specification

Download the OpenAPI definition: https://api.apify.com/v2/actors/xTVk32iI15Tyag7bZ/builds/JTULHVqV2TpvKLcYW/openapi.json
