API reference · Catalogue
Create or update products
Batch upsert from your store, keyed on your own product id. At most 200 products per request, 100 variants per product.
Request
curl -X POST "https://icebot.icebergaisolutions.com/api/v1/catalogue/products" \
-H "Authorization: Bearer $ICEBOT_API_KEY" \
-H "Content-Type: application/json" \
-d '{"source":"woocommerce","products":[{"external_id":"101","name":"Nasi lemak ayam goreng","price":12.9,"sku":"NL-AYAM","stock":40,"category":"Mains"},{"external_id":"102","name":"Teh tarik","price":3.5,"variants":[{"external_id":"102-R","name":"Regular","price":3.5,"stock":null},{"external_id":"102-L","name":"Large","price":4.5,"stock":null}]}]}'Body
| Field | Type | Description |
|---|---|---|
source | api | woocommerce | shopify | Where the data came from. Default api. |
products[].external_id (required) | string | number | Your store's product id. Unique per request. |
products[].name (required) | string | Up to 300 characters. |
products[].price | number | Ringgit, non-negative. Only MYR is supported. |
products[].stock | integer | null | 12 = twelve in stock, 0 = sold out, null = not tracked (sell without limit), absent = leave unchanged. |
products[].description, category, sku, image_url, is_active | various | Optional. is_active defaults to true. |
products[].variants[] | array | Each { external_id, name, sku?, price?, is_active?, stock? }. Absent = variants untouched; [] = the product has none now. |
{
"source": "woocommerce",
"products": [
{
"external_id": "101",
"name": "Nasi lemak ayam goreng",
"price": 12.9,
"sku": "NL-AYAM",
"stock": 40,
"category": "Mains"
},
{
"external_id": "102",
"name": "Teh tarik",
"price": 3.5,
"variants": [
{
"external_id": "102-R",
"name": "Regular",
"price": 3.5,
"stock": null
},
{
"external_id": "102-L",
"name": "Large",
"price": 4.5,
"stock": null
}
]
}
]
}Responses
200
Per-item results, even when some failed, so you can retry exactly those.
{
"data": [
{
"external_id": "101",
"status": "created",
"id": "0a7d3e21-5c44-4b8e-9f10-6e2d8c9b1a37"
},
{
"external_id": "102",
"status": "updated",
"id": "1b8e4f32-6d55-4c9f-8a21-7f3e9d0c2b48"
}
],
"created": 1,
"updated": 1,
"failed": 0
}Errors
Every endpoint can also return 401 (missing, unknown or revoked key), 403 (origin not allowed, or the key lacks catalogue:sync) and 429 (rate limited). See Errors.
| Status | error | When |
|---|---|---|
400 | invalid body | The batch is malformed; nothing was written. details lists every problem with its index. |
Source of truth: /api/v1/catalogue/products in apps/dashboard/app/api/v1/catalogue/products/route.ts.