Woolworths NZ Scraper: Prices, Specials & Club Deals
Pricing
from $2.40 / 1,000 products
Woolworths NZ Scraper: Prices, Specials & Club Deals
Get Woolworths New Zealand prices for milk, bread and weekly specials. Collect store prices, regular and member offers, promotion dates, unit prices, stock, barcode, brand and size by postcode, category or product. About $0.003 per product, or $3 for 1,000. No login.
Pricing
from $2.40 / 1,000 products
Rating
0.0
(0)
Developer
fortbrand
Maintained by CommunityActor stats
0
Bookmarked
2
Total users
1
Monthly active users
a day ago
Last modified
Categories
Share
For retail price analysts, grocery brands and comparison sites monitoring Woolworths New Zealand. Collect verified-store prices, specials, member offers, unit prices, stock and current barcodes.
Actor fees are USD; product prices are NZD. About $0.003 per product at one store. Twenty product-store rows cost about $0.06, plus Apify's small start charge. Optional ingredients and nutrition are included in that product price. You do not need a Woolworths account, Everyday Rewards login or a separate data subscription.
What you get
Each product response must confirm the selected pickup address and fulfilment store. Default-store substitutions are retried, then reported as free notes if the requested context cannot be recovered.
| Field | Meaning |
|---|---|
verdict | A readable price, store and availability summary. |
retailer, country, currency | Woolworths New Zealand, NZ and NZD. |
storeId, storeName | The fulfilment store ID and store name actually reported with the price. |
location | The requested four-digit postcode, preserving leading zeros; null for a store-ID or default-store request. |
productId, sku | Woolworths numeric product stockcode. |
gtin | Current product-service barcode for the selected selling unit. The original catalogue identifier is retained separately. |
title, brand, size | Catalogue product name, brand and pack information. |
price | Current ordinary, non-member price in NZD. A member-only offer is kept separately. |
regularPrice | The source reference price, including the non-member price for a member offer. |
onSale | A current special or member-price flag supplied by the source. |
promoText, promoType | Available promotion labels and the kind of offer. |
promoStart, promoEnd | Published promotion timestamps, or null. Dates are never guessed from a weekly promotion cycle. |
memberPrice, memberProgram | Everyday Rewards member price and programme when a club-price offer is published. |
unitPrice, unitOfMeasure | Ordinary unit price and its published measure, such as 1L or 100G. |
inStock | The site's in-stock or out-of-stock signal. Null means it did not give a clear signal. |
stockLevel | Null. The API's stock-level integers are availability codes, not physical shelf counts. |
rating, reviewCount | Null when the source does not publish these in the product data. Customer review text is not collected. |
category | Published category path or the category used to find the item. |
url, imageUrl | Public product page and product image. |
scrapedAt | UTC observation time, retained when a run resumes. |
Retailer-specific extras include catalogueBarcode, catalogueBarcodeDiffers, canonicalVariantKey, canonicalBarcodes, categoryPaths, sellingUnit, stockcode, cupPrice, cupMeasure, cupListPrice, isNew, pickupAddressId, fulfilmentMethod, siteDisplayedPrice, memberUnitPrice, availabilityStatus, stockStatusCode, multibuy, bonusPoints, savingsAmount and savingsPercent.
With includeDetails, rows can also contain ingredients, allergens, nutrition, origins, description, directions and health star rating. detailsStatus says whether those details were included, were not requested, or could not be read. An absent ingredient list does not establish that a product contains no ingredients or allergens.
Choose a store deliberately
locations accepts NZ pickup-store postcodes, for example 0629, 8051, 9016, 9371 and 2022. These are exact matches against the retailer's public pickup directory. If several pickup stores have the same postcode, the first store by name is selected and its actual name appears in every row. An unknown postcode produces a free note; it is never replaced with Glenfield or another default store.
Use public pickup-address IDs in storeIds: Northlands 1225718, Glenfield 1190273. Reuse the output's pickupAddressId in this input. The separate storeId is the fulfilment ID the retailer reports after selection. For example, the verified Northlands context reported pickup address 1225718 and fulfilment store 9540 during validation.
Empty location lists use the site's explicit signed-out default, not a national average. Pickup and delivery prices can differ. Preserve storeId, pickupAddressId and fulfilmentMethod, even when store names look similar.
Start in three steps
- Enter a search term, paste a category or product link, or supply product stockcodes.
- Choose postcodes or pickup-address IDs and set the run-wide
maxItemscap. - Run the Actor, read the summary and export JSON, CSV or Excel from the dataset.
The prefill searches milk in 0629, capped at 20 products. A 29 October cloud run delivered 20 products in 18 seconds. Validation passed 38 varied cloud inputs and 100-product pagination. Ten products were hand-checked across five selected stores.
Input examples
Search at one store:
{"searchTerms": ["milk"],"locations": ["0629"],"maxItemsPerSearch": 20,"maxItems": 20}
Compare a small basket across five pickup areas:
{"searchTerms": ["milk"],"locations": ["0629", "8051", "9016", "9371", "2022"],"maxItemsPerSearch": 2,"maxItems": 20}
Browse a department or a precise shelf:
{"startUrls": ["https://www.woolworths.co.nz/shop/browse/fridge-deli/milk/full-cream-milk"],"storeIds": ["1225718"],"maxItemsPerSearch": 30,"maxItems": 30}
Collect current coffee deals:
{"searchTerms": ["coffee"],"locations": ["8051"],"dealsOnly": true,"maxItemsPerSearch": 100,"maxItems": 20}
Fetch known product details:
{"productIds": ["282764", "282768"],"locations": ["0629"],"includeDetails": true,"maxItems": 2}
| Input | Default and behaviour |
|---|---|
searchTerms | Optional list. Milk is used when no source input is supplied. |
startUrls | Optional search, browse, specials or product links on woolworths.co.nz. |
productIds | Optional numeric stockcodes. Current and older product URL formats are accepted too. |
locations | Four-digit pickup-store postcodes. Empty means the site's default context. |
storeIds | Optional public pickup-address IDs. Duplicate selections of one store are combined. |
maxItemsPerSearch | 20 product candidates examined per source and store. Filters and duplicates can reduce delivered rows. |
maxItems | 20 unique product-store rows across the entire run, not 20 per store. |
dealsOnly | False. Keep specials, member, multibuy or points offers when true. |
includeDetails | False. Adds slower product-detail requests at no extra product fee. |
proxyConfiguration | Verified NZ residential route. Custom proxy URLs or an explicit direct configuration are honoured. |
A specials URL walks the current public departments and retains actual offer rows. A regular low shelf price alone is not treated as a discount. maxItemsPerSearch limits candidates examined, so a narrow search with few specials may return fewer deal rows than maxItems.
Output example from a real run
This shortened record is from the 29 October 2026 prefill validation; prices are observations at that time:
{"verdict": "$8.09 at Woolworths Glenfield; in stock.","retailer": "Woolworths New Zealand","country": "NZ","currency": "NZD","storeId": "9443","storeName": "Woolworths Glenfield","location": "0629","productId": "6038845","sku": "6038845","gtin": "94153835","title": "Anchor Lactose Free Milk Blue 2L","price": 8.09,"regularPrice": 8.09,"memberPrice": null,"unitPrice": 4.05,"unitOfMeasure": "1L","inStock": true,"stockLevel": null,"pickupAddressId": "1190273","fulfilmentMethod": "Pickup"}
Dataset views cover prices, offers and details. The free DEALS record contains offers only. SUMMARY reports counts, stores, notes, duplicates, coverage and spending-limit stops.
Free note rows have recordType: "NOTE", a readable verdict and a noteId. Product rows have productId. Filter on productId when your downstream table should contain products only.
Pricing and spending controls
| Job | Product charge before plan discounts |
|---|---|
| 20 products at one store | $0.06 |
| 100 product-store rows | $0.30 |
| 1,000 product-store rows | $3.00 |
| 20 products at five stores, if all 100 rows are requested and found | $0.30 |
The start charge is $0.00005 at the 512 MB default. Bronze product pricing is $0.00285, Silver $0.0027 and Gold $0.0024. Higher tiers use the Gold product rate. Apify platform and the configured Apify proxy usage are included in the Actor price; a separately supplied proxy may have its own provider charges.
One product at one store is one unit, deduplicated across all inputs. That product at two stores is two price observations and two units. Failed inputs, invalid links, empty results, filtered candidates, duplicates and summaries have no Product charge.
The Actor checks available spending room before saving another paid row. If there is no room for the next product, it stops cleanly and keeps the products already delivered. A restart recovers saved rows and acknowledged charges, including an interruption between saving the row and receiving its charge acknowledgement.
Monitor prices every day
Save a task with a fixed search, shelf or basket and an explicit store list. In Apify's Schedules, create a daily schedule for that task. Each run creates a dated snapshot, so retain scrapedAt and the store identifiers when you append exports to your database or spreadsheet.
Keep the pickup address and fulfilment method constant. Compare ordinary and member prices separately, and compare unit prices only when their published measures match. A member offer ending does not establish an ordinary shelf-price increase.
Each scheduled run is a fresh snapshot; unchanged products are not suppressed. Append finished datasets through webhooks, Make, Zapier, n8n, Sheets or your ingestion job. Read SUMMARY before treating a scan as complete.
API use
Python:
from apify_client import ApifyClientclient = ApifyClient("YOUR_APIFY_TOKEN")run = client.actor("vant47/woolworths-nz-scraper").call(run_input={"searchTerms": ["milk"],"locations": ["0629"],"maxItems": 20})for row in client.dataset(run["defaultDatasetId"]).iterate_items():if row.get("productId"):print(row["storeName"], row["title"], row["price"])
JavaScript:
import { ApifyClient } from 'apify-client';const client = new ApifyClient({ token: process.env.APIFY_TOKEN });const run = await client.actor('vant47/woolworths-nz-scraper').call({searchTerms: ['coffee'], locations: ['8051'], maxItems: 20});const { items } = await client.dataset(run.defaultDatasetId).listItems();
HTTP:
curl -X POST \-H "Authorization: Bearer $APIFY_TOKEN" \-H "Content-Type: application/json" \--data '{"searchTerms":["milk"],"locations":["0629"],"maxItems":20}' \'https://api.apify.com/v2/acts/vant47~woolworths-nz-scraper/run-sync-get-dataset-items'
Use with AI agents (MCP)
Connect an MCP client to https://mcp.apify.com and ask it to use vant47/woolworths-nz-scraper. A useful request names the retailer, postcode or pickup-address ID, product terms and maximum row count: “Get 20 Woolworths NZ milk prices at postcode 0629, including unit prices and member offers.”
Agents use the same input fields, dataset and SUMMARY. Set the run-wide cap for all intended product-store combinations. API aliases query, queries, keywords, url and urls are also accepted.
Known limits and FAQ
Are these national prices? No. They are prices for the verified pickup context or the default context the site actually supplied. Neither is labelled a national average.
Does a postcode choose a delivery address? No. It selects an exact matching pickup-store postcode. No personal address, account or delivery checkout is used. A postcode without a published pickup-store match gives a free note.
Which barcode is returned? gtin comes from the current product service. catalogueBarcode preserves the older catalogue identifier, which can differ. Multiple selling units are matched explicitly; an ambiguous barcode stays null.
Does stockLevel: 3 mean three items? No. Source stock-level values are status codes. They are retained as stockStatusCode; the family stockLevel quantity stays null. inStock follows the site's availability text.
What if promotions have no dates? promoStart and promoEnd stay null. Offers are checked against product details for published dates. Timestamps remain exactly as supplied, including any missing timezone offset.
What happens when details fail? A verified listing row can still be delivered at the ordinary Product price with detailsStatus: "unavailable". No detail surcharge exists.
What if the retailer refuses requests? Requests are paced and retried on fresh sessions. Store selection is repeated and checked on recovery. Inputs still unavailable after retries produce free notes; other inputs can continue.
Which connection works? NZ residential HTTP is the production route. Direct and datacenter HTTP failed cloud checks. Headed Chrome is used for independent storefront validation. Custom proxies are optional.
Can I resume a migrated or rebooted run? Yes. Saved pages, product-store identities and acknowledged charges are recovered within that run. A new independent run is a fresh snapshot and charges its delivered products again.
Can I export only deals? Yes. Read the free DEALS JSON record, use dealsOnly for a filtered dataset, or inspect offer fields in the dataset's deals view.
Does this collect shoppers or reviews? No. It reads public grocery catalogue and anonymous store-context data. Customer profiles, account cookies, personal shopping lists and review text are outside the collection.