Skip to main content

Concepts

The few ideas every endpoint, alert and webhook is built on. Read this once and the rest of the API reads plainly.

Sources​

A source is one online store we read: nearly always a brand's own. It has a short name (source, such as source_3) that every record and filter uses, and a display name.

GET /api/v1/sources lists every source we read, with its kind. The ones your plan opens come first, with their counts and when each was last checked (last_checked). The rest are listed by name and size only, with open: false. Asking for a locked source by name is refused with 402 source_locked.

Products and variants​

A product is one model at one source: its name, brand, category, description, images and page. A variant is one colour or size of it. Each variant has its own price, list price, stock and specs, so a price or a stock change always belongs to a variant.

  • Ids are UUIDs, and stay the same for as long as we track the product: store them to recognise a product or variant on your side.
  • Lists give a product's price as a range across its variants (price_from to price_to). One product's page gives every variant.
  • Specs (such as weight, dimensions and material) are what the source states. What it does not state is left out, never guessed.

Markets and money​

Every price is in the source's own market: region is a country code (ISO 3166-1, such as US) and currency a currency code (ISO 4217, such as USD). Prices are never converted, and never compared across currencies.

FieldExampleWhat it is
price"229.00"The price now, as an exact decimal string.
price_minor22900The same in minor units (cents): an integer, safe to add up.
list_price"249.00"The price before any sale, as the source states it.
on_saletrueThe price is below the list price.
discount_pct8How far below, in whole percent.

Use the string or the integer, not a float: 0.1 + 0.2 is not 0.3 in floating point.

Time and freshness​

Every time is ISO 8601 in UTC, ending in Z. first_seen_at is when we first read a product, observed_at when a price was read, and occurred_at when a change was found.

Most sources are read about every two hours. A read that fails, or that a store blocks, records nothing: no change, and never "out of stock". The last known values stay, so missing data and a real change are never confused.

Changes (events)​

Each change is an event with an id. Ids rise in the order events are recorded, which is how the feed is followed (Pagination). An event exists only when the change was stored, and is never edited afterwards. There are ten kinds, in three groups:

typeGroupMeans
new_productassortmentA product appeared on a source.
new_variantassortmentA product gained a colour or size.
price_downpriceA variant's price fell.
price_uppriceA variant's price rose.
sale_startedpriceA variant went on sale: its price is now below its list price.
sale_endedpriceA variant came off sale.
back_in_stockstockA variant that was out of stock can be bought again.
out_of_stockstockA variant sold out.
product_goneassortmentA product left its source.
product_backassortmentA product that had left its source is listed again.

A product counts as gone (product_gone) only after it has been missing from complete reads of its store for about a day and a half, so a page that failed to load once is not a product that left. GET /api/v1/event-types returns this list, and needs no key.

Alerts​

An alert is a saved filter on the feed. Its matches show on your account's Alerts page and at GET /api/v1/alerts/feed, and with "channel": "webhook" each is also posted to your address (Webhooks). Every field is optional: left out, it matches any source, category, product and kind of change.

note

A new alert's webhook hears of what happens from then on (last_event_id), not of the past.

Plans and what you can read​

Your plan decides which sources are open; every feature works on every plan. Lists and the feed include only open sources, and naming a locked one is refused with 402. Limits per plan are in Errors & limits.