# Shopify Scraper: Products, Prices & Stock Monitor — Cartlark (`cybermax/shopify-scraper`) Actor

Shopify and WooCommerce product scraper: every product of any store with prices, compare-at (sale) prices, discount %, stock per variant, SKU, vendor, tags and images. Monitor mode returns only price drops, new products and stock changes. $0.80 per 1,000 products, no start fee.

- **URL**: https://apify.com/cybermax/shopify-scraper.md
- **Developed by:** [CyberMax](https://apify.com/cybermax) (community)
- **Categories:** E-commerce, Lead generation, Automation
- **Security:** Limited permissions
- **Stats:** 2 total users, 1 monthly users, 0.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

$0.80 / 1,000 product delivereds

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.

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

## Cartlark: Shopify Scraper — Products, Prices & Stock Monitor (also WooCommerce)

#### Every product, price, sale price and stock level of any Shopify or WooCommerce store, and an alert when they change

Paste a store URL and get its whole catalogue as clean rows: title, price range, compare-at (was) price, discount %, stock per variant, SKU, vendor, type, tags, images and link. Turn on monitor mode, schedule it, and you only get (and only pay for) what changed: price drops and rises with the % change, new products, out-of-stock and back-in-stock. Works with Shopify and WooCommerce, detected automatically. **$0.80 per 1,000 products, no start fee.**

**[▶ Try it now with a prefilled input](https://apify.com/cybermax/shopify-scraper)** · $0.0008 per product (a 250-product store = $0.20) · no start fee · Apify's free plan includes $5 of credit a month

**Built for:** e-commerce brands watching competitors' prices · dropshippers and resellers researching products · agencies auditing a client's catalogue · price-comparison and deal sites · market researchers · AI agents that need a store's live catalogue

**Real output** (real run on Apify, 10 Nov 2026: 2 stores, 10 products in 5 s, platform cost $0.0001; four rows shown):

| Product | Price | Was | Currency | In stock | Variants | Platform |
|---|---|---|---|---|---|---|
| Women's Wool Runner NZ - Shadow Blue | 120 | | USD | 12 of 13 sizes | 13 | Shopify |
| Women's Wool Cruiser - Port | 120 | | USD | 3 of 13 sizes | 13 | Shopify |
| All Star Canvas Hi Converse | 29 | | USD | yes | 20 | WooCommerce |
| Varanise CN Tee Hilfiger Denim | 15 | 19 | USD | yes | | WooCommerce |

```json
{"stores": ["https://www.allbirds.com"], "maxProductsPerStore": 20}
```

### Ready-made inputs (one click)

| Job | Input | Result |
|---|---|---|
| **Whole catalogue** | `{"stores": ["competitor.com"]}` | Every product (up to 250; raise `maxProductsPerStore` for more). |
| **One collection** | `{"stores": ["https://shop.com/collections/sale"]}` | Just that Shopify collection. |
| **What's on sale** | `{"stores": ["shop1.com", "shop2.com"], "onlyOnSale": true}` | Products priced below their compare-at price, with discount %. |
| **Product research** | `{"stores": ["shop.com"], "keywords": ["hoodie", "jacket"], "maxPrice": 80}` | Matching products under $80. |
| **Price & stock alerts** | `{"stores": ["competitor.com"], "monitor": true, "monitorKey": "competitors"}` | On a schedule: only new products, price changes and stock changes. |

### Use cases

- **Competitor price monitoring:** a daily scheduled run on your competitors' stores, with a Slack or email ping when a price drops or a product sells out.
- **Restock and drop alerts:** know the moment a sold-out product is back or a new collection lands.
- **Product research for dropshipping and resale:** best sellers, price points, vendors and tags across many stores in one table.
- **Catalogue audits:** missing SKUs, products without images, out-of-stock items, sale prices left on by mistake.
- **Feeds for comparison sites and AI agents:** clean JSON with a stable shape for both platforms.

### Output fields

| Field | What it is |
|---|---|
| `platform`, `store`, `productId`, `url` | Where the product lives. |
| `title`, `vendor`, `productType`, `tags`, `sku` | Product details (WooCommerce: categories and tags go into `tags`, the first category into `productType`). |
| `price`, `priceMax`, `currency` | Lowest and highest variant price, in the store's currency. |
| `compareAtPrice`, `onSale`, `discountPercent` | The "was" price and the discount when the product is on sale. |
| `available`, `variantsAvailable`, `variantCount` | In stock at all, how many variants are in stock, how many variants exist. |
| `variants[]` | Each variant: id, title, SKU, price, compare-at price, in stock, options (size/colour). Shopify. |
| `image`, `imageCount` | Main image URL and number of images. |
| `rating`, `reviewCount` | WooCommerce product rating, when the store shows one. |
| `description` | Plain text, when `includeDescription` is on. |
| `createdAt`, `publishedAt`, `updatedAt`, `scrapedAt` | Dates (Shopify gives all three). |
| `change`, `previousPrice`, `priceChange`, `priceChangePercent`, `previousAvailable` | Monitor mode only: `new`, `price`, `compare_at_price`, `out_of_stock`, `back_in_stock` or `variants`. |

A run summary per store (platform found, products scanned and delivered, and the reason when a store could not be read) is saved as the `OUTPUT` record.

### Input

| Field | What it does |
|---|---|
| `stores` | Store domains or URLs. A Shopify `/collections/<name>` URL limits the run to that collection. |
| `maxProductsPerStore` | Default 250. In monitor mode: how many products per store are watched. |
| `keywords`, `minPrice`, `maxPrice`, `onlyAvailable`, `onlyOnSale` | Filters. Filtered-out products are free. |
| `includeVariants`, `includeDescription` | Row detail. |
| `platform` | `auto` (default), `shopify` or `woocommerce`. |
| `monitor`, `monitorKey` | Only changes since the last monitor run with the same watchlist. |
| `proxyConfiguration` | Optional, for stores that rate-limit. |

### Run it on a schedule (price and stock alerts)

1. Open the Actor, set `{"stores": ["competitor-a.com", "competitor-b.com"], "monitor": true, "monitorKey": "competitors"}` and save it as a **task**.
2. **Schedules → Create**: daily at 07:00 (cron `0 7 * * *`), pointing at the task.
3. Add an integration on the task: Slack, email or a webhook "when the run succeeds". The first run records the catalogue; every later run returns only what changed, so a quiet day costs almost nothing.

### Integrations

- **Google Sheets / Make / Zapier / n8n:** use the Apify app or node and map the dataset fields (title, price, compareAtPrice, available, change).
- **API (curl):**
  ```bash
  curl -X POST "https://api.apify.com/v2/acts/cybermax~shopify-scraper/run-sync-get-dataset-items?token=YOUR_TOKEN" \
    -H "Content-Type: application/json" -d '{"stores": ["https://www.allbirds.com"], "maxProductsPerStore": 20}'
  ```
- **Python:** `ApifyClient(token).actor("cybermax/shopify-scraper").call(run_input={"stores": ["allbirds.com"]})`
- **AI agents (MCP):** add `cybermax/shopify-scraper` to the Apify MCP server (`https://mcp.apify.com?actors=cybermax/shopify-scraper`) so Claude, Cursor or any MCP client can ask "what does this store sell, and at what price?".

### Why Cartlark

| | Cartlark | Typical Shopify product scraper on the Store |
|---|---|---|
| Platforms | Shopify **and** WooCommerce, detected per store | Usually one platform per Actor |
| Change monitoring | Built in: price changes with %, stock in/out, new products; unchanged = free | Rare |
| Sale data | Compare-at price, discount %, on-sale filter | Often raw prices only |
| Variants | Every variant's price, SKU and stock | Varies, sometimes a paid add-on |
| Price | $0.80 per 1,000 products, no start fee | $1 to $10 per 1,000, some with a start fee (Store prices on 10 Nov 2026) |

### FAQ

**Which stores work?** Any Shopify store and any WooCommerce store that has the standard public catalogue switched on (most do). Password-protected stores, stores that disable these endpoints, and stores whose robots.txt disallows them are skipped, and the summary says why. Other platforms (Wix, BigCommerce, Magento) are not supported.

**Is it legal?** Cartlark reads only the public product catalogue a storefront serves to every visitor, the same data shown on its product pages, and it follows each store's robots.txt. It collects no customer or personal data. Use the data in line with the laws that apply to you.

**Why not write my own script?** You can; Cartlark saves the edge cases: both platforms in one shape, minor-unit prices, variable products, pagination limits, rate limits with retries, robots.txt, and change detection with state kept between runs.

**How much will a run cost?** $0.0008 per product delivered, nothing else. A 1,000-product store is $0.80; a daily monitor on a 500-product store that changes 10 prices costs about $0.01 a day.

**Can I get more than 250 products?** Yes, set `maxProductsPerStore` up to 50,000.

### Also from CyberMax

- [Auditmoss: SEO Audit Crawler](https://apify.com/cybermax/seo-audit) · find broken links and on-page SEO issues on any store or site.
- [Unfurlwren: Meta Tags & Open Graph Extractor](https://apify.com/cybermax/meta-tags-extractor) · titles, descriptions and schema for any list of URLs.
- [Bouncefern: Bulk URL Status & Redirect Checker](https://apify.com/cybermax/url-status-checker) · check thousands of product links at once.

Found this useful? A quick rating helps others find it.

© 2026 CyberMax. All rights reserved.

# Actor input Schema

## `stores` (type: `array`):

Shopify or WooCommerce stores, e.g. allbirds.com or https://www.allbirds.com. A Shopify collection URL (…/collections/mens) scrapes just that collection. The platform is detected for you.

## `maxProductsPerStore` (type: `integer`):

In monitor mode: how many products per store are watched.

## `keywords` (type: `array`):

Optional. Keep products whose title, vendor, type or tags contain any of these words.

## `minPrice` (type: `integer`):

Optional, in the store's currency.

## `maxPrice` (type: `integer`):

Optional, in the store's currency.

## `onlyAvailable` (type: `boolean`):

Skip products with no variant in stock.

## `onlyOnSale` (type: `boolean`):

Keep products priced below their compare-at (regular) price.

## `includeVariants` (type: `boolean`):

Each product row lists its variants (size/colour) with price, compare-at price, SKU and stock. Off = one compact row per product.

## `includeDescription` (type: `boolean`):

Adds the product description as plain text (up to 5,000 characters).

## `platform` (type: `string`):

Leave on auto unless you know the platform.

## `monitor` (type: `boolean`):

For scheduled runs. Remembers every product it saw and returns only new products, price changes (with previous price and % change), compare-at changes, out-of-stock and back-in-stock events. Nothing changed = nothing charged.

## `monitorKey` (type: `string`):

Optional name for this watchlist's saved state (use different names for different watchlists).

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

Optional. Only needed if a store rate-limits your requests.

## Actor input object example

```json
{
  "stores": [
    "https://www.allbirds.com"
  ],
  "maxProductsPerStore": 20,
  "onlyAvailable": false,
  "onlyOnSale": false,
  "includeVariants": true,
  "includeDescription": false,
  "platform": "auto",
  "monitor": false,
  "proxyConfiguration": {
    "useApifyProxy": false
  }
}
```

# Actor output Schema

## `results` (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 = {
    "stores": [
        "https://www.allbirds.com"
    ],
    "maxProductsPerStore": 20,
    "proxyConfiguration": {
        "useApifyProxy": false
    }
};

// Run the Actor and wait for it to finish
const run = await client.actor("cybermax/shopify-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 = {
    "stores": ["https://www.allbirds.com"],
    "maxProductsPerStore": 20,
    "proxyConfiguration": { "useApifyProxy": False },
}

# Run the Actor and wait for it to finish
run = client.actor("cybermax/shopify-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 '{
  "stores": [
    "https://www.allbirds.com"
  ],
  "maxProductsPerStore": 20,
  "proxyConfiguration": {
    "useApifyProxy": false
  }
}' |
apify call cybermax/shopify-scraper --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,cybermax/shopify-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/ETAmohqK38Oh0GDmY/builds/7DFj0hpyRjCLJtMNh/openapi.json
