# Ace Hardware Scraper (`crawlerbros/acehardware-scraper`) Actor

Scrape acehardware.com - browse departments (Tools, Lawn & Garden, Paint, Plumbing, Hardware, and more) or look up products by ID/URL. Get title, price, brand, category, description, images, rating, reviews, and stock availability.

- **URL**: https://apify.com/crawlerbros/acehardware-scraper.md
- **Developed by:** [Crawler Bros](https://apify.com/crawlerbros) (community)
- **Categories:** E-commerce, Automation, Agents
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $3.00 / 1,000 results

This Actor is paid per event and usage. You are charged both the fixed price for specific events and for Apify platform usage.
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 a software tools running on the Apify platform, for all kinds of web data extraction and automation use cases.
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.

In JavaScript/TypeScript projects, use official [JavaScript/TypeScript client](https://docs.apify.com/api/client/js/docs.md):

```bash
npm install apify-client
```

In Python projects, use official [Python client library](https://docs.apify.com/api/client/python/docs.md):

```bash
pip install apify-client
```

In shell scripts, use [Apify CLI](https://docs.apify.com/cli/docs.md):

````bash
# MacOS / Linux
curl -fsSL https://apify.com/install-cli.sh | bash
# Windows
irm https://apify.com/install-cli.ps1 | iex
```bash

In AI frameworks, you might use the [Apify MCP server](https://docs.apify.com/integrations/mcp.md).

If your project is in a different language, use 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

## Ace Hardware Scraper

Scrape [Ace Hardware](https://www.acehardware.com) — one of the largest hardware and home-improvement retail chains in the US. Browse any department (Tools, Lawn & Garden, Paint, Plumbing, Hardware, and more) or look up specific products by ID or URL. Get title, price, brand, category, description, images, customer rating/reviews, and stock availability — no login, cookies, or API key required.

### What this actor does

- **Three modes:** browse a department/category, look up products by ID, or look up products by URL
- **15 top-level departments** exposed as a dropdown, plus an advanced free-text sub-category URL override for granular browsing (e.g. "Power Tools > Cordless Drills")
- **Filters:** keyword, price range, minimum rating, brand, in-stock only, on-sale only
- **Real pricing:** current price, original list price, sale flag, and discount %
- **Empty fields are omitted** — every field in the output actually has data

### Output per product

- `productId` — Ace Hardware's internal product/item code
- `title`, `description`, `shortDescription`
- `brand`
- `department`, `category`, `categoryBreadcrumb[]`
- `price`, `currency`, `onSale`, `listPrice`, `discountPercent` (when on sale)
- `inStock`, `availability` (`In Stock` / `Out of Stock`)
- `upc`, `manufacturerPartNumber`
- `supportsDelivery`, `supportsInStorePickup`
- `rating` (0–5), `reviewCount`
- `countryOfOrigin` — ISO country code (e.g. `US`, `CN`, `VN`)
- `whatsInTheBox` — box-contents description, for kits/bundles
- `packageDimensions` (`length`/`width`/`height`/`unit`), `packageWeight` (`value`/`unit`) — shipping measurements
- `images[]`, `mainImage`
- `features[]` — marketing bullet points
- `sourceUrl`, `productUrl`
- `recordType: "product"`, `scrapedAt`

### Input

| Field | Type | Default | Description |
|---|---|---|---|
| `mode` | string | `byCategory` | `byCategory` / `byProductIds` / `byProductUrls` |
| `department` | string | `tools` | Top-level department to browse (mode=byCategory) |
| `categoryUrl` | string | – | Advanced: any acehardware.com department/sub-category URL, overrides `department` |
| `keyword` | string | – | Only keep products whose title/description/brand/category contains this text |
| `productIds` | array | – | Numeric product IDs (mode=byProductIds) |
| `productUrls` | array | – | Full product page URLs (mode=byProductUrls) |
| `minPrice` / `maxPrice` | number | – | Price range in USD |
| `minRating` | number | – | Minimum customer rating (0–5); drops unrated products |
| `inStockOnly` | boolean | `false` | Only emit purchasable/in-stock products |
| `onSaleOnly` | boolean | `false` | Only emit products currently discounted below list price |
| `brand` | string | – | Only keep products from a matching brand |
| `maxItems` | integer | `20` | Hard cap on emitted records (1–500) |

#### Example: browse Tools, cordless items only, under $300, in stock

```json
{
  "mode": "byCategory",
  "department": "tools",
  "keyword": "cordless",
  "maxPrice": 300,
  "inStockOnly": true,
  "maxItems": 50
}
````

#### Example: a specific sub-category

```json
{
  "mode": "byCategory",
  "categoryUrl": "https://www.acehardware.com/departments/tools/power-tools/powered-screwdrivers",
  "maxItems": 30
}
```

#### Example: lookup by product ID

```json
{
  "mode": "byProductIds",
  "productIds": ["2192375", "2611648", "70555"]
}
```

### Use cases

- **Price monitoring** — track price and discount changes for specific SKUs over time
- **Assortment research** — see which brands and products a department carries
- **Market research** — compare hardware/home-improvement pricing across retailers
- **Inventory alerts** — filter `inStockOnly` to catch back-in-stock items
- **Catalog enrichment** — pull structured product data (images, specs, ratings) for a set of known product IDs

### FAQ

**Do I need to log in or provide cookies?**  No. Every field is scraped from public, unauthenticated pages.

**Does this cost extra for proxies?**  No. The actor runs without any proxy configuration on Apify's free datacenter access.

**Can I search acehardware.com by free-text keyword sitewide?**  Not directly — see Limitations below. Use the `keyword` filter together with `mode=byCategory` to search within a department, or use `byProductIds`/`byProductUrls` if you already know the products.

**Why is `discountPercent` missing on some products?**  It's only included when the product is actually on sale (current price below the list price). Full-price products correctly omit it rather than showing `0`.

**Why is `rating` missing on some products?**  Not every product has customer reviews yet. Fields that can't be populated with real data are omitted rather than filled with placeholders.

**What departments are available?**  Tools; Lawn & Garden; Outdoor Power Equipment; Paint & Supplies; Plumbing; Hardware; Lighting & Electrical; Heating & Cooling; Home & Decor; Building Supplies; Storage & Organization; Outdoor Living; Automotive, RV & Marine; Grills & Smokers; Ace YardRx.

**Can I browse a narrower sub-category than the top-level department?**  Yes — paste any acehardware.com category page URL into `categoryUrl` (advanced field), and the actor resolves it automatically.

### Limitations

- **Sitewide free-text search is not supported.** acehardware.com's `/search` page is disallowed in `robots.txt` and is protected by a Cloudflare Turnstile challenge that blocks every zero-cost access method (plain HTTP and browser-impersonation requests alike). Category browsing (with the in-category `keyword` filter) and direct product ID/URL lookup are used instead, and reliably return full pricing and product data.
- Only products currently listed on acehardware.com are returned; discontinued/delisted items are not available.
- Pricing, availability, and ratings reflect the online storefront at scrape time and may differ from in-store pricing at a specific Ace location.

# Actor input Schema

## `mode` (type: `string`):

What to fetch.

## `department` (type: `string`):

Top-level department to browse. Ignored if `categoryUrl` is set.

## `categoryUrl` (type: `string`):

Optional: paste any acehardware.com department or sub-category page URL (e.g. `https://www.acehardware.com/departments/tools/power-tools/powered-screwdrivers`) to browse a specific sub-category instead of a whole top-level department. Overrides `department` when set.

## `keyword` (type: `string`):

Only keep products whose title, description, brand, or category contains this text (case-insensitive). Filters within the selected department/category — acehardware.com's sitewide search page is Cloudflare-protected and not reliably reachable, so this narrows the browse results instead. See README Limitations.

## `productIds` (type: `array`):

Ace Hardware numeric product/item codes, e.g. `2192375`.

## `productUrls` (type: `array`):

Full acehardware.com product page URLs, or short `https://www.acehardware.com/product/<id>` links.

## `minPrice` (type: `number`):

Drop products priced below this amount.

## `maxPrice` (type: `number`):

Drop products priced above this amount.

## `minRating` (type: `number`):

Drop products with a customer rating below this value, or with no rating yet.

## `inStockOnly` (type: `boolean`):

Only emit products currently purchasable/in stock online.

## `onSaleOnly` (type: `boolean`):

Only emit products currently discounted below their list price.

## `brand` (type: `string`):

Only keep products whose brand contains this text (case-insensitive), e.g. `Milwaukee`, `DeWalt`, `Ace`.

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

Hard cap on emitted product records.

## Actor input object example

```json
{
  "mode": "byCategory",
  "department": "tools",
  "productIds": [],
  "productUrls": [],
  "inStockOnly": false,
  "onSaleOnly": false,
  "maxItems": 20
}
```

# Actor output Schema

## `products` (type: `string`):

Dataset containing all scraped Ace Hardware products.

# 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 = {
    "mode": "byCategory",
    "department": "tools",
    "productIds": [],
    "productUrls": [],
    "inStockOnly": false,
    "onSaleOnly": false,
    "maxItems": 20
};

// Run the Actor and wait for it to finish
const run = await client.actor("crawlerbros/acehardware-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 = {
    "mode": "byCategory",
    "department": "tools",
    "productIds": [],
    "productUrls": [],
    "inStockOnly": False,
    "onSaleOnly": False,
    "maxItems": 20,
}

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

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

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

```

## CLI example

```bash
echo '{
  "mode": "byCategory",
  "department": "tools",
  "productIds": [],
  "productUrls": [],
  "inStockOnly": false,
  "onSaleOnly": false,
  "maxItems": 20
}' |
apify call crawlerbros/acehardware-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "command": "npx",
            "args": [
                "mcp-remote",
                "https://mcp.apify.com/?tools=crawlerbros/acehardware-scraper",
                "--header",
                "Authorization: Bearer <YOUR_API_TOKEN>"
            ]
        }
    }
}

```

## OpenAPI specification

```json
{
    "openapi": "3.0.1",
    "info": {
        "title": "Ace Hardware Scraper",
        "description": "Scrape acehardware.com - browse departments (Tools, Lawn & Garden, Paint, Plumbing, Hardware, and more) or look up products by ID/URL. Get title, price, brand, category, description, images, rating, reviews, and stock availability.",
        "version": "1.0",
        "x-build-id": "7zChUIbEVKFv0y1Lg"
    },
    "servers": [
        {
            "url": "https://api.apify.com/v2"
        }
    ],
    "paths": {
        "/acts/crawlerbros~acehardware-scraper/run-sync-get-dataset-items": {
            "post": {
                "operationId": "run-sync-get-dataset-items-crawlerbros-acehardware-scraper",
                "x-openai-isConsequential": false,
                "summary": "Executes an Actor, waits for its completion, and returns Actor's dataset items in response.",
                "tags": [
                    "Run Actor"
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "$ref": "#/components/schemas/inputSchema"
                            }
                        }
                    }
                },
                "parameters": [
                    {
                        "name": "token",
                        "in": "query",
                        "required": true,
                        "schema": {
                            "type": "string"
                        },
                        "description": "Enter your Apify token here"
                    }
                ],
                "responses": {
                    "200": {
                        "description": "OK"
                    }
                }
            }
        },
        "/acts/crawlerbros~acehardware-scraper/runs": {
            "post": {
                "operationId": "runs-sync-crawlerbros-acehardware-scraper",
                "x-openai-isConsequential": false,
                "summary": "Executes an Actor and returns information about the initiated run in response.",
                "tags": [
                    "Run Actor"
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "$ref": "#/components/schemas/inputSchema"
                            }
                        }
                    }
                },
                "parameters": [
                    {
                        "name": "token",
                        "in": "query",
                        "required": true,
                        "schema": {
                            "type": "string"
                        },
                        "description": "Enter your Apify token here"
                    }
                ],
                "responses": {
                    "200": {
                        "description": "OK",
                        "content": {
                            "application/json": {
                                "schema": {
                                    "$ref": "#/components/schemas/runsResponseSchema"
                                }
                            }
                        }
                    }
                }
            }
        },
        "/acts/crawlerbros~acehardware-scraper/run-sync": {
            "post": {
                "operationId": "run-sync-crawlerbros-acehardware-scraper",
                "x-openai-isConsequential": false,
                "summary": "Executes an Actor, waits for completion, and returns the OUTPUT from Key-value store in response.",
                "tags": [
                    "Run Actor"
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "$ref": "#/components/schemas/inputSchema"
                            }
                        }
                    }
                },
                "parameters": [
                    {
                        "name": "token",
                        "in": "query",
                        "required": true,
                        "schema": {
                            "type": "string"
                        },
                        "description": "Enter your Apify token here"
                    }
                ],
                "responses": {
                    "200": {
                        "description": "OK"
                    }
                }
            }
        }
    },
    "components": {
        "schemas": {
            "inputSchema": {
                "type": "object",
                "required": [
                    "mode"
                ],
                "properties": {
                    "mode": {
                        "title": "Mode",
                        "enum": [
                            "byCategory",
                            "byProductIds",
                            "byProductUrls"
                        ],
                        "type": "string",
                        "description": "What to fetch.",
                        "default": "byCategory"
                    },
                    "department": {
                        "title": "Department (mode=byCategory)",
                        "enum": [
                            "tools",
                            "lawn-and-garden",
                            "outdoor-power-equipment",
                            "paint-and-supplies",
                            "plumbing",
                            "hardware",
                            "lighting-and-electrical",
                            "heating-and-cooling",
                            "home-and-decor",
                            "building-supplies",
                            "storage-and-organization",
                            "outdoor-living",
                            "automotive-rv-and-marine",
                            "grills-smokers",
                            "ace-yardrx"
                        ],
                        "type": "string",
                        "description": "Top-level department to browse. Ignored if `categoryUrl` is set.",
                        "default": "tools"
                    },
                    "categoryUrl": {
                        "title": "Category/sub-category URL (mode=byCategory, advanced)",
                        "type": "string",
                        "description": "Optional: paste any acehardware.com department or sub-category page URL (e.g. `https://www.acehardware.com/departments/tools/power-tools/powered-screwdrivers`) to browse a specific sub-category instead of a whole top-level department. Overrides `department` when set."
                    },
                    "keyword": {
                        "title": "Keyword filter (mode=byCategory)",
                        "type": "string",
                        "description": "Only keep products whose title, description, brand, or category contains this text (case-insensitive). Filters within the selected department/category — acehardware.com's sitewide search page is Cloudflare-protected and not reliably reachable, so this narrows the browse results instead. See README Limitations."
                    },
                    "productIds": {
                        "title": "Product IDs (mode=byProductIds)",
                        "type": "array",
                        "description": "Ace Hardware numeric product/item codes, e.g. `2192375`.",
                        "default": [],
                        "items": {
                            "type": "string"
                        }
                    },
                    "productUrls": {
                        "title": "Product URLs (mode=byProductUrls)",
                        "type": "array",
                        "description": "Full acehardware.com product page URLs, or short `https://www.acehardware.com/product/<id>` links.",
                        "default": [],
                        "items": {
                            "type": "string"
                        }
                    },
                    "minPrice": {
                        "title": "Min price (USD)",
                        "minimum": 0,
                        "maximum": 1000000,
                        "type": "number",
                        "description": "Drop products priced below this amount."
                    },
                    "maxPrice": {
                        "title": "Max price (USD)",
                        "minimum": 0,
                        "maximum": 1000000,
                        "type": "number",
                        "description": "Drop products priced above this amount."
                    },
                    "minRating": {
                        "title": "Min rating (0-5)",
                        "minimum": 0,
                        "maximum": 5,
                        "type": "number",
                        "description": "Drop products with a customer rating below this value, or with no rating yet."
                    },
                    "inStockOnly": {
                        "title": "In stock only",
                        "type": "boolean",
                        "description": "Only emit products currently purchasable/in stock online.",
                        "default": false
                    },
                    "onSaleOnly": {
                        "title": "On sale only",
                        "type": "boolean",
                        "description": "Only emit products currently discounted below their list price.",
                        "default": false
                    },
                    "brand": {
                        "title": "Brand filter",
                        "type": "string",
                        "description": "Only keep products whose brand contains this text (case-insensitive), e.g. `Milwaukee`, `DeWalt`, `Ace`."
                    },
                    "maxItems": {
                        "title": "Max items",
                        "minimum": 1,
                        "maximum": 500,
                        "type": "integer",
                        "description": "Hard cap on emitted product records.",
                        "default": 20
                    }
                }
            },
            "runsResponseSchema": {
                "type": "object",
                "properties": {
                    "data": {
                        "type": "object",
                        "properties": {
                            "id": {
                                "type": "string"
                            },
                            "actId": {
                                "type": "string"
                            },
                            "userId": {
                                "type": "string"
                            },
                            "startedAt": {
                                "type": "string",
                                "format": "date-time",
                                "example": "2025-01-08T00:00:00.000Z"
                            },
                            "finishedAt": {
                                "type": "string",
                                "format": "date-time",
                                "example": "2025-01-08T00:00:00.000Z"
                            },
                            "status": {
                                "type": "string",
                                "example": "READY"
                            },
                            "meta": {
                                "type": "object",
                                "properties": {
                                    "origin": {
                                        "type": "string",
                                        "example": "API"
                                    },
                                    "userAgent": {
                                        "type": "string"
                                    }
                                }
                            },
                            "stats": {
                                "type": "object",
                                "properties": {
                                    "inputBodyLen": {
                                        "type": "integer",
                                        "example": 2000
                                    },
                                    "rebootCount": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "restartCount": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "resurrectCount": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "computeUnits": {
                                        "type": "integer",
                                        "example": 0
                                    }
                                }
                            },
                            "options": {
                                "type": "object",
                                "properties": {
                                    "build": {
                                        "type": "string",
                                        "example": "latest"
                                    },
                                    "timeoutSecs": {
                                        "type": "integer",
                                        "example": 300
                                    },
                                    "memoryMbytes": {
                                        "type": "integer",
                                        "example": 1024
                                    },
                                    "diskMbytes": {
                                        "type": "integer",
                                        "example": 2048
                                    }
                                }
                            },
                            "buildId": {
                                "type": "string"
                            },
                            "defaultKeyValueStoreId": {
                                "type": "string"
                            },
                            "defaultDatasetId": {
                                "type": "string"
                            },
                            "defaultRequestQueueId": {
                                "type": "string"
                            },
                            "buildNumber": {
                                "type": "string",
                                "example": "1.0.0"
                            },
                            "containerUrl": {
                                "type": "string"
                            },
                            "usage": {
                                "type": "object",
                                "properties": {
                                    "ACTOR_COMPUTE_UNITS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATASET_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATASET_WRITES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "KEY_VALUE_STORE_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "KEY_VALUE_STORE_WRITES": {
                                        "type": "integer",
                                        "example": 1
                                    },
                                    "KEY_VALUE_STORE_LISTS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "REQUEST_QUEUE_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "REQUEST_QUEUE_WRITES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATA_TRANSFER_INTERNAL_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATA_TRANSFER_EXTERNAL_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "PROXY_SERPS": {
                                        "type": "integer",
                                        "example": 0
                                    }
                                }
                            },
                            "usageTotalUsd": {
                                "type": "number",
                                "example": 0.00005
                            },
                            "usageUsd": {
                                "type": "object",
                                "properties": {
                                    "ACTOR_COMPUTE_UNITS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATASET_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATASET_WRITES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "KEY_VALUE_STORE_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "KEY_VALUE_STORE_WRITES": {
                                        "type": "number",
                                        "example": 0.00005
                                    },
                                    "KEY_VALUE_STORE_LISTS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "REQUEST_QUEUE_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "REQUEST_QUEUE_WRITES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATA_TRANSFER_INTERNAL_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATA_TRANSFER_EXTERNAL_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "PROXY_SERPS": {
                                        "type": "integer",
                                        "example": 0
                                    }
                                }
                            }
                        }
                    }
                }
            }
        }
    }
}
```
