Skip to main content
Version: next

Entities

The data you push is a stream of entities — one NDJSON line per entity in a snapshot, one operation per entity in an /events batch. Every entity shares one envelope; only the payload differs by kind.

The envelope

{
"kind": "<entity_kind>",
"external_id": "<your-stable-id>",
"lang": "<locale | null>",
"translation_of": "<external_id | null>",
"payload": { /* kind-specific */ }
}
  • kind — the discriminator; one of the 16 kinds below.
  • external_id — your stable, opaque id. Canonical shape <source>:<kind>:<id> (e.g. wc:product:iphone-15-pro, laravel:category:42). The backend stores it verbatim and upserts on it; parent references use the same shape.
  • lang / translation_of — optional locale tag and a pointer to the original entity for translations.

In an /events batch the same fields appear inside each operation, with type (upsert / delete) and an optional deleted_at.

The 16 kinds

KindPurpose
siteSingle-row store basics — name, url, locale, currency, timezone.
environmentSingle-row technical landscape — platform, plugins, capabilities (diagnostic).
productThe catalog item. Richest payload; carries inline variations.
variationA single product variation (inline in product, or standalone in a delta).
categoryProduct category; supports a parent reference + optional available_filters / available_sorts that ground the bot's filtering & sorting (see Capabilities).
tagProduct tag.
attributeA taxonomy-level attribute (e.g. pa_color) and its possible values.
pageA content page; content_text feeds retrieval.
postA blog post (same shape as page).
cptA custom post type (same shape as page).
menuA navigation menu with a recursive item tree.
menu_itemA flat, normalized navigation item.
formA site form (fields, submit endpoint, intent hint).
popupA site popup (triggers, intent hint).
shipping_methodAn offered shipping method.
payment_methodAn offered payment method.

A backend that doesn't recognise a kind dead-letters it rather than failing the batch, so a newer producer can introduce a kind ahead of the backend.

Three rules that matter

These are the mistakes that silently produce wrong answers, so they are worth stating plainly:

  • Money is integer minor units. 549.99 UAH is 54999 — never a float, never a string. Applies to price_amount, regular_price_amount, sale_price_amount. currency is a separate ISO-4217 string.
  • categories and tags are slug lists["smartphones", "apple"], not objects, not numeric ids.
  • page.content_text is plain text — strip HTML and decode entities; this is what retrieval reads. (content_html may carry the original markup separately for rendering.)

Required fields

Almost everything is optional with a default. The fields you can't omit:

  • productname
  • page / post / cpttitle
  • formplugin, title, submit_endpoint
  • variation (standalone) → parent_external_id

Unknown extra fields are ignored, so adding a field your backend doesn't know yet won't fail validation.

Product — the canonical payload

{
"kind": "product",
"external_id": "wc:product:iphone-15-pro-256gb",
"lang": "uk_UA",
"payload": {
"sku": "APL-IP15P-256",
"name": "Apple iPhone 15 Pro 256GB",
"slug": "iphone-15-pro-256gb",
"product_type": "variable",
"price_amount": 54999,
"regular_price_amount": 59999,
"currency": "UAH",
"description": "Флагман Apple з чіпом A18 Pro та титановим корпусом.",
"stock_status": "instock",
"stock_quantity": 14,
"permalink": "https://shop.example.com/product/iphone-15-pro-256gb/",
"categories": ["smartphones", "apple"],
"tags": ["new", "premium", "5g"],
"attributes": [
{ "name": "Колір", "slug": "pa_color", "options": ["Blue Titanium", "White Titanium"], "variation": true }
],
"variations": [
{ "external_id": "wc:variation:12345", "sku": "APL-IP15P-256-BLU",
"price_amount": 54999, "stock_status": "instock", "attributes": { "pa_color": "Blue Titanium" } }
],
"images": [
"https://cdn.example.com/iphone-15-pro-blue-1.jpg",
"https://cdn.example.com/iphone-15-pro-blue-2.jpg"
]
}
}

Notable fields: product_type is one of simple | variable | grouped | external; stock_status is a string (instock / outofstock / onbackorder), never a bool; images is a flat URL list with the primary first; variations are inline for variable products. A single variation can also be pushed standalone in a delta with a parent_external_id.

Next

  • Errors — the error shape and retry semantics.