# ALDI US Scraper: Store Prices, ALDI Finds & Weekly Ad (`vant47/aldi-us-scraper`) Actor

Get ALDI US products with the price at your store: regular price, Price Drops and weekly ad deals with dates, ALDI Finds, unit price, stock, size and category. Search, categories or product links by ZIP or store. Pairs with our ALDI Australia Scraper. About $0.0035 per product. No login.

- **URL**: https://apify.com/vant47/aldi-us-scraper.md
- **Developed by:** [fortbrand](https://apify.com/vant47) (community)
- **Categories:** E-commerce, Automation
- **Security:** Limited permissions
- **Stats:** 3 total users, 2 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $2.80 / 1,000 products

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/actors/running/actors-in-store.md#pay-per-event

## What's an Apify Actor?

An Actor is a serverless cloud program that runs on the Apify platform. It has two run modes.
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.

Apify vocabulary and the platform model are defined once, in the agent quickstart at https://apify.com/agents.md.

## 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.

Do not guess an integration path. Every one of them is in the agent quickstart at https://apify.com/agents.md: the Apify MCP server, Agent Skills with the Apify CLI, the JavaScript and Python clients, the REST API, and the account-free path for an agent with no human to sign in. It also carries the rule on stating cost before the first paid run.

For examples already wired to this Actor's own input schema, see the [API](#api) section below.

Each client library has reference documentation the quickstart does not restate: [JavaScript/TypeScript](https://docs.apify.com/api/client/js/docs.md) (`npm install apify-client`) and [Python](https://docs.apify.com/api/client/python/docs.md) (`pip install apify-client`).

# README

## ALDI US Scraper: Store Prices, ALDI Finds & Weekly Ad

For grocery price analysts, brands and comparison services that need the advertised **in-store price at a verified ALDI US location**. Search for cheese, milk or coffee, follow category and product links, or monitor a stable basket of product IDs. About **$0.0035 per delivered product**, so **20 products cost $0.07** and **1,000 products cost $3.50**, plus the minimum **$0.00005 Actor start charge**. No retailer login or retailer API key is required.

The Safeway & Albertsons family schema, Product event, views and SUMMARY are preserved. Products at different stores are separate observations; overlapping inputs at one store are delivered and charged once.

### Promotion coverage on small jobs

Every row identifies its `promotionCoverage`. Sources with at least 20 candidates within the limits, and larger known-product baskets, add the store-wide weekly-ad, ALDI Finds and Price Drops scan. Small jobs use product-response and requested-source promotions. Weekly-ad URLs retain their dates; dated Finds collections retain their on-sale dates. Small exact-product or keyword lookups can have null weekly-ad/Finds fields because the broader scan was not performed. Product sale flags and supplied promotion objects remain. SUMMARY identifies coverage.

### Know which price you are comparing

ALDI publishes separate in-store, pickup and delivery contexts. This Actor selects **in-store** and verifies its retailer location ID. `priceChannel` is `in_store`; `shopId` identifies the channel and `storeId` the physical location. Select In-Store and the same store when checking a row manually.

`price` is the advertised current price. `regularPrice` is an explicit original price, otherwise null. Flyer membership and ALDI Finds do not automatically prove a markdown. `onSale` preserves the source flag; `isDeal` also covers known weekly-ad and Price Drops membership.

Weekly-ad dates come from the flyer range. Finds dates come from dated collections. Coupons remain separate and are not subtracted from price. Member prices and UPCs stay null without source evidence.

For weighted goods, `priceIsEstimate`, `estimatedWeight` and `estimatedWeightUnit` retain the package estimate; unitPrice retains the published price per pound. Prices exclude checkout charges. Availability is an online estimate, not a physical shelf count.

### What you get

Each product begins with a readable verdict, then shared retail fields and ALDI evidence. Unknown values stay null.

| Field | Meaning |
| --- | --- |
| `retailer`, `country`, `currency` | ALDI, US and USD. |
| `storeId`, `storeName`, `location` | Verified public ALDI location, supplied store name and requested ZIP. Location is null for exact-store/default selections. |
| `productId`, `sku`, `gtin` | Public product number, explicit SKU and barcode where supplied. A product ID is never presented as a UPC. |
| `title`, `brand`, `size` | Product title, supplied brand and pack size. |
| `price`, `regularPrice`, `onSale` | Advertised in-store price, published original price and source sale flag. |
| `promoText`, `promoType` | Weekly-ad name, Price Drop label or supplied promotion information. |
| `promoStart`, `promoEnd` | Published weekly-ad date range when this product belongs to that ad. |
| `memberPrice`, `memberProgram` | Explicit membership price/program, otherwise null. |
| `unitPrice`, `unitOfMeasure` | Numeric unit comparison price and the printed unit, such as oz, fl oz or lb. |
| `inStock`, `stockLevel` | Supplied availability boolean and numeric quantity, if published. Qualitative labels do not become invented quantities. |
| `rating`, `reviewCount` | Explicit aggregate review values when supplied. |
| `category`, `url`, `imageUrl` | Supplied category, public product page and product image. |
| `scrapedAt` | UTC observation timestamp. |

ALDI-specific fields:

| Field | Meaning |
| --- | --- |
| `banner` | `aldi`, for joins with the rest of the grocery family. |
| `aldiFind`, `aldiFindOnSaleDate` | Membership in a published ALDI Finds collection and its dated on-sale label. |
| `weeklyAd`, `weeklyAdName` | Current flyer membership and its published name. |
| `priceDrop`, `fanFavorite` | Explicit collection or tag evidence where available. |
| `department`, `brandType` | Supplied taxonomy and ALDI-exclusive/national brand tag when explicit. |
| `sellByWeight`, `snapEligible` | Public selling-unit and SNAP information when shown. |
| `stockStatus`, `stockStatusText` | Original qualitative availability code and shopper-facing wording. |
| `unitPriceText`, `aisle` | Original comparison-price string and in-store location label. |
| `offers`, `digitalCouponAvailable`, `digitalCouponText` | Supplied promotion objects and coupon signals; no personalized redemption calculation. |
| `shopId`, `priceChannel` | Verified in-store shopping context. |
| `storeAddress`, `storeDistance`, `requestedLocations` | Public store-selection evidence and ZIPs resolving to the store. |
| `details` | Optional product sections and images, including ingredients/warnings when published. |
| `sourceUrl`, `sourceJobId`, `recordType` | Reproducible public source request, job identifier and PRODUCT/NOTE distinction. |

The overview view groups price, promotion, unit price, stock and store. The deals view adds dates; details exposes the full schema. Free DEALS JSON contains only known deals; large exports link to parts.

Every run saves `SUMMARY` with products, stores, deals found, charged products, duplicate exclusions, resolved stores, source outcomes, free failures and spending-limit status. Explanatory dataset rows have `recordType: "NOTE"` and no Product charge. Product observations have `recordType: "PRODUCT"`.

### Start in three steps

1. Enter ZIP codes or exact ALDI location IDs.
2. Choose terms, category/deals/product links or product IDs, and set the cap.
3. Run, inspect SUMMARY, then export JSON, CSV or Excel.

On 3 November 2026, the cheese prefill near 60174 returned 20 products and matching charges in 40.3 seconds, with no source failures. Larger cloud validations also completed cleanly:

| Input mode | Products | Stores with products | Product charges |
| --- | ---: | ---: | ---: |
| Search terms | 1,200 | 4 | 1,200 |
| Category pages | 1,200 | 3 | 1,200 |
| Known-product basket | 1,176 | 3 | 1,176 |

All three completed without duplicate rows or source failures.

### Inputs and examples

| Input | Behavior |
| --- | --- |
| `searchTerms` | Array such as `["milk", "coffee"]`. Each term is searched at each selected store. Only the site's exact-result groups are accepted; unrelated recommendation carousels are excluded. |
| `startUrls` | Public ALDI US category pages, collections, weekly ads, search links or product links. Explicit run selections control the store. |
| `productIds` | Numeric ALDI product IDs, such as `18649227`. These are not UPC barcodes. |
| `locations` | US ZIP codes. The nearest in-store location returned by ALDI is selected using the ZIP's geographic center. |
| `storeIds` | Exact public retailer location IDs, such as `23593`. They take precedence over ZIPs. |
| `maxItemsPerSearch` | Maximum new rows per term, category or deals source and store, default 20, maximum 1,000. Known-product ID lists use the global maxItems cap. |
| `maxItems` | Global product/store row cap, default 20, maximum 10,000. |
| `dealsOnly` | Keep source markdowns, Price Drops and weekly-ad products. ALDI Finds alone are not automatically a price discount. |
| `includeDetails` | Add optional product sections and images with no extra product fee. |
| `proxyConfiguration` | Default datacenter pool first, US residential after refusal; custom settings are supported. |

Empty locations/storeIds use the website default. ZIP centers select ALDI nearby-store listings and can differ from a street-address lookup. Pin the returned storeId for repeatable monitoring.

Compare a small basket across ZIPs:

```json
{
  "searchTerms": ["milk", "coffee"],
  "locations": ["60174", "10001"],
  "maxItemsPerSearch": 20,
  "maxItems": 80
}
```

Monitor exact products at two stores:

```json
{
  "productIds": ["18649227", "18649581"],
  "storeIds": ["23593", "20785"],
  "maxItems": 4
}
```

Read a department or a particular collection:

```json
{
  "startUrls": [
    "https://www.aldi.us/store/aldi/pages/dairy-and-eggs",
    "https://www.aldi.us/store/aldi/collections/n-milk-33852"
  ],
  "storeIds": ["23593"],
  "maxItemsPerSearch": 100,
  "maxItems": 100
}
```

Weekly-ad URL: `https://www.aldi.us/store/aldi/flyers/view/weekly/print`. Finds URL: `https://www.aldi.us/store/aldi/pages/this-weeks-aldi-finds`. Structured catalogs are read; image-only panels are not OCRed.

### Example from a real cloud run

Observed on 3 November 2026 at ALDI W. Main Street, St. Charles:

```json
{
  "retailer": "ALDI",
  "storeId": "20785",
  "location": "60174",
  "productId": "18649581",
  "title": "Happy Farms American Cheese Singles",
  "brand": "happy farms",
  "size": "12 oz",
  "price": 1.85,
  "regularPrice": null,
  "unitPrice": 0.15,
  "unitOfMeasure": "oz",
  "inStock": true,
  "brandType": "ALDI exclusive",
  "priceChannel": "in_store"
}
```

### Pricing and spending limits

One Product is one distinct product/store observation. Each run charges for fresh observations; within-run duplicates are free.

| Products | Base | Bronze | Silver | Gold |
| --- | --- | --- | --- | --- |
| 20 | $0.07 | $0.0665 | $0.063 | $0.056 |
| 100 | $0.35 | $0.3325 | $0.315 | $0.28 |
| 1,000 | $3.50 | $3.325 | $3.15 | $2.80 |

Add the minimum $0.00005 Actor start charge. Base is $0.0035 per Product, Bronze $0.003325, Silver $0.00315 and Gold $0.0028. Notes, summaries, duplicates and failed or empty requests add no Product charge. Optional details have no additional event fee. There is no extra default dataset-row charge.

Remaining charge capacity is checked before additional batches. The Actor stops cleanly at the spending limit and records it in SUMMARY. Caps do not guarantee available matches.

### Monitor prices every day

Save a task with stable store IDs and product IDs or collection URLs. In Apify Console, create a schedule, select the task, choose its time/timezone, and connect a completed-run webhook to your workflow.

Join snapshots with `banner + storeId + productId`, retaining `scrapedAt`. Keep current price, original price, flyer dates and Finds dates separate. Read SUMMARY before accepting complete coverage. Source failures produce free notes rather than substituted old prices.

Save snapshots in your database for history; no historical backfill or cross-run suppression is provided. Make, Zapier, n8n and Sheets can consume the dataset and summary.

### API and automation

Use your Apify token:

```bash
curl -X POST \
  'https://api.apify.com/v2/acts/vant47~aldi-us-scraper/runs' \
  -H 'Authorization: Bearer YOUR_APIFY_TOKEN' \
  -H 'Content-Type: application/json' \
  -d '{"searchTerms":["cheese"],"locations":["60174"],"maxItems":20}'
```

```python
from apify_client import ApifyClient
client = ApifyClient("YOUR_APIFY_TOKEN")
run = client.actor("vant47/aldi-us-scraper").call(
    run_input={"productIds": ["18649227"], "storeIds": ["23593"], "maxItems": 1}
)
rows = list(client.dataset(run["defaultDatasetId"]).iterate_items())
summary = client.key_value_store(run["defaultKeyValueStoreId"]).get_record("SUMMARY")
```

```javascript
import { ApifyClient } from 'apify-client';
const client = new ApifyClient({ token: process.env.APIFY_TOKEN });
const run = await client.actor('vant47/aldi-us-scraper').call({
  searchTerms: ['cheese'], locations: ['60174'], maxItems: 20
});
const { items } = await client.dataset(run.defaultDatasetId).listItems();
```

### Use with AI agents (MCP)

Connect to `https://mcp.apify.com`. Request ALDI US prices by ZIP/store, supply a product cap, and ask for SUMMARY. Preserve nulls, physical store IDs and the in-store price channel when combining retailers.

### Reliability and limits

Requests are sequential and paced. Refusals retry with fresh anonymous sessions, using US residential after datacenter where needed. Retry-After is honored. No retailer account, account cookies or CAPTCHA solving is used.

Saved batches, progress and the dataset ledger survive reboots. Delivery and charging are serial; recovery reconciles rows, receipts and platform counts. Ambiguous billing evidence stops further charges. Both private reboot tests finished with unique rows and matching charges.

Search accepts the site's exact-result groups. Category HTML supplies navigation; inventory and prices are then fetched for the selected store. This does not guarantee every visual panel or the entire national catalog. Missing verified prices are excluded without a Product charge.

Finds can remain in older dated collections. Their dates do not guarantee stock. Availability labels remain qualitative. Missing UPCs, card prices, SNAP flags, quantities and coupon conditions stay null. Details can contain only a nutrition heading when values are absent. Prices and stock can change after observation. The Actor is independent of ALDI.

### FAQ

**Can I pin a store?** Yes, reuse a returned storeId in storeIds.

**Why does the website price differ?** Check the physical store and In-Store mode.

**Is every flyer item discounted?** No. Flyer membership and markdowns are separate.

**Are UPCs complete?** No. gtin remains null without a verified barcode.

**Do details add a fee?** No extra Product fee; they add requests.

**What happens with bad input?** Parseable invalid selections produce free notes and SUMMARY. Apify can reject schema-invalid input before startup, without a Product charge.

**Can I combine the grocery family?** Yes, preserve each retailer's store identity and price rules alongside the shared fields.

Related: [Safeway & Albertsons](https://apify.com/vant47/safeway-albertsons-scraper), [ALDI Australia](https://apify.com/vant47/aldi-australia-scraper).

ZIP lookup uses [Zippopotam.us](https://api.zippopotam.us/), adapted from [GeoNames](https://www.geonames.org/) under the [Open Database License](https://opendatacommons.org/licenses/odbl/1-0/). ALDI supplies store coordinates, addresses, products and prices.

# Actor input Schema

## `searchTerms` (type: `array`):

Find products such as milk, chicken or coffee. Each term is searched at every selected store. Leave empty when using only URLs or product IDs.

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

ALDI US category pages, collections, weekly ads or product links. Explicit ZIPs and store IDs control prices.

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

Optional numeric ALDI product IDs, such as 18649227. These are product IDs, not UPCs.

## `locations` (type: `array`):

Use US ZIP codes, such as 94611 or 20037. Chooses the nearest store of the selected banner. Empty means the website default store.

## `storeIds` (type: `array`):

Exact public ALDI retailer location IDs, such as 23593. These take precedence over ZIPs. Every store and in-store price list is verified.

## `maxItemsPerSearch` (type: `integer`):

Maximum new product rows from each term, category or deals source at one store. Duplicates are free.

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

Global limit across product and store observations. About $0.0035 per product: 20 products cost $0.07 plus the small start fee.

## `dealsOnly` (type: `boolean`):

Keep source markdowns, Price Drops and weekly-ad products. ALDI Finds alone are not automatically a discount.

## `includeDetails` (type: `boolean`):

Slower optional product metadata such as ingredients and nutrition. No extra product fee. Missing details remain null; store prices are always verified independently.

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

Default datacenter pool first, then US residential after refusal. Fresh anonymous visitor sessions only.

## Actor input object example

```json
{
  "searchTerms": [
    "cheese"
  ],
  "locations": [
    "60174"
  ],
  "maxItemsPerSearch": 20,
  "maxItems": 20,
  "dealsOnly": false,
  "includeDetails": false,
  "proxyConfiguration": {
    "useApifyProxy": true
  }
}
```

# Actor output Schema

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

No description

## `dealsView` (type: `string`):

No description

## `dealsOnly` (type: `string`):

No description

## `summary` (type: `string`):

No description

# 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 = {
    "searchTerms": [
        "cheese"
    ],
    "locations": [
        "60174"
    ],
    "maxItemsPerSearch": 20,
    "maxItems": 20
};

// Run the Actor and wait for it to finish
const run = await client.actor("vant47/aldi-us-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 = {
    "searchTerms": ["cheese"],
    "locations": ["60174"],
    "maxItemsPerSearch": 20,
    "maxItems": 20,
}

# Run the Actor and wait for it to finish
run = client.actor("vant47/aldi-us-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 '{
  "searchTerms": [
    "cheese"
  ],
  "locations": [
    "60174"
  ],
  "maxItemsPerSearch": 20,
  "maxItems": 20
}' |
apify call vant47/aldi-us-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,vant47/aldi-us-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/pt2vFrQwJpq8Bp6Sk/builds/cEnleGNZFfczNY3Wd/openapi.json
