Wocart
Wocart API

Store API

Server

Get store configuration

GET
https://api.wocart.store
/store/config
X-Store-API-Key (header)

Get store settings used by the storefront (theme, locale, branding).

Get store configuration › query Parameters

locale
​string · maxLength: 35

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

theme
​string · pattern: ^(?=.{1,64}$)[a-z][a…

The requesting theme's key (defineTheme({ key })). Its text edits ride along as contentOverrides; without it there are none.

The requesting theme's key (defineTheme({ key })). Its text edits ride along as contentOverrides; without it there are none.

Get store configuration › Responses

200

Store configuration

success
​boolean · required
​StoreConfig · required

Get a menu

GET
https://api.wocart.store
/store/menus/{handle}
X-Store-API-Key (header)

A navigation menu by handle, as a shopper sees it: labels in the requested language (?locale=, else the store's primary), each item's href a path of the store without a language prefix (or the merchant's URL). An item whose destination is deleted or not public is left out with its children. An unknown handle is a 404: the theme then renders its own fallback.

Get a menu › path Parameters

handle
​string · pattern: ^[a-z0-9][a-z0-9-]{0… · required

Lowercase letters, digits and hyphens; how a theme names the menu

Lowercase letters, digits and hyphens; how a theme names the menu

Get a menu › query Parameters

locale
​string · maxLength: 35

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

Get a menu › Responses

The menu

success
​boolean · required
​StorefrontMenu · required

Get a collection

GET
https://api.wocart.store
/store/collections/{handle}
X-Store-API-Key (header)

A collection's title and description for its page (/collections/:handle), in the requested language (?locale=, else the store's primary). Its products come from /store/products?collection=. An unknown handle is a 404: the theme answers a real 404 page.

Get a collection › path Parameters

handle
​string · pattern: ^[a-z0-9][a-z0-9-]{0… · required

Lowercase letters, digits and hyphens; how a theme names the collection

Lowercase letters, digits and hyphens; how a theme names the collection

Get a collection › query Parameters

locale
​string · maxLength: 35

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

Get a collection › Responses

The collection

success
​boolean · required
​StorefrontCollection · required

List store products

GET
https://api.wocart.store
/store/products
X-Store-API-Key (header)

Get the public product catalog for the storefront. Only returns products where status=ACTIVE, showInStore=true and visibility=true.

List store products › query Parameters

collection
​string · pattern: ^[a-z0-9][a-z0-9-]{0…

Only this collection's products (by handle), in the merchant's order. An unknown handle lists nothing.

Only this collection's products (by handle), in the merchant's order. An unknown handle lists nothing.

onSale
​string · enum

When true, only products priced below their compare-at price.

When true, only products priced below their compare-at price.

Enum values:
true
false
categoryId
​string

Filter by category ID.

Filter by category ID.

sort
​string · enum

The order: newest, price-ascending or price-descending. Absent: a collection's own order, a search's best match first, else newest.

The order: newest, price-ascending or price-descending. Absent: a collection's own order, a search's best match first, else newest.

Enum values:
newest
price-ascending
price-descending
limit
​integer · min: 1 · max: 100

Maximum number of products to return. Server cap: 100.

Maximum number of products to return. Server cap: 100.

Default: 24
offset
​integer | null · min: 0

Products to skip, for paging through the whole catalog (e.g. a sitemap).

Products to skip, for paging through the whole catalog (e.g. a sitemap).

Default: 0
locale
​string · maxLength: 35

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

List store products › Responses

200

List of products

success
​boolean · required
​StoreProductList[] · required
count
​integer · required

Number of items in data

total
​integer · required

Number of products in the whole listing, across its pages


Search store products

GET
https://api.wocart.store
/store/search
X-Store-API-Key (header)

The products a shopper's words find, with the list endpoint's gates, filters, paging and sort; without a sort, products whose name holds every word come first. Its own path, so a server without search answers 404 rather than the whole catalog.

Search store products › query Parameters

q
​string · minLength: 1 · maxLength: 100 · required

What the shopper typed. Every word must be in the product's name — the catalog's or the requested language's — or its tags; case is ignored for Latin letters.

What the shopper typed. Every word must be in the product's name — the catalog's or the requested language's — or its tags; case is ignored for Latin letters.

collection
​string · pattern: ^[a-z0-9][a-z0-9-]{0…

Only this collection's products (by handle), in the merchant's order. An unknown handle lists nothing.

Only this collection's products (by handle), in the merchant's order. An unknown handle lists nothing.

onSale
​string · enum

When true, only products priced below their compare-at price.

When true, only products priced below their compare-at price.

Enum values:
true
false
categoryId
​string

Filter by category ID.

Filter by category ID.

sort
​string · enum

The order: newest, price-ascending or price-descending. Absent: a collection's own order, a search's best match first, else newest.

The order: newest, price-ascending or price-descending. Absent: a collection's own order, a search's best match first, else newest.

Enum values:
newest
price-ascending
price-descending
limit
​integer · min: 1 · max: 100

Maximum number of products to return. Server cap: 100.

Maximum number of products to return. Server cap: 100.

Default: 24
offset
​integer | null · min: 0

Products to skip, for paging through the whole catalog (e.g. a sitemap).

Products to skip, for paging through the whole catalog (e.g. a sitemap).

Default: 0
locale
​string · maxLength: 35

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

Search store products › Responses

200

The products found

success
​boolean · required
​StoreProductList[] · required
count
​integer · required

Number of items in data

total
​integer · required

Number of products in the whole listing, across its pages


Get store product

GET
https://api.wocart.store
/store/products/{handle}
X-Store-API-Key (header)

Get a single product by its URL handle. Same visibility filters as the list endpoint. Returns parsed variantOptions, tags, joined category, active variants, all images, and offers — the active Buy X Get Y promotions currently applicable to this product.

Get store product › path Parameters

handle
​string · required

Get store product › query Parameters

locale
​string · maxLength: 35

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

Get store product › Responses

200

Product details

success
​boolean · required
​StoreProductDetail · required

Get published landing page

GET
https://api.wocart.store
/store/landing-pages/{slug}
X-Store-API-Key (header)

Get a published landing page by its public slug: the ordered image stack, spacing settings, the linked product in its full store-product shape (variants, offers, inventory) in the requested language (?locale=), so the storefront order form works unmodified, and the page's own document for the requesting ?theme=. Store-hidden products (showInStore=false) still render here — the landing page is their sales channel; the catalog list and the product's own page stay hidden. Draft/archived/unknown slugs return 404; with ?preview=1 a draft answers too. Each successful GET increments the page's view counter (non-unique in v1), except a preview.

Get published landing page › path Parameters

slug
​string · required

Get published landing page › query Parameters

locale
​string · maxLength: 35

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

theme
​string · pattern: ^(?=.{1,64}$)[a-z][a…

The requesting theme's key (defineTheme({ key })): the page's own document for that theme comes with it.

The requesting theme's key (defineTheme({ key })): the page's own document for that theme comes with it.

preview
​string · enum

1 for an editor's preview: a draft page answers too, and no visit is counted. Never sent for a shopper's page.

1 for an editor's preview: a draft page answers too, and no visit is counted. Never sent for a shopper's page.

Enum values:
1

Get published landing page › Responses

Published landing page with its product

success
​boolean · required
​StoreLandingPage · required

Get a published store page

GET
https://api.wocart.store
/store/pages/{slug}
X-Store-API-Key (header)

Get a Terms/Privacy/Refund/Shipping/custom page by its public slug, in the requested language (?locale=, else the store's primary). Falls back to the primary, then to whichever locale exists, only when the requested language has no translation for this page; the actual locale served is in the response's locale field. Draft or unknown slugs return 404 — never a soft 200 with empty content.

Get a published store page › path Parameters

slug
​string · required

Get a published store page › query Parameters

locale
​string · maxLength: 35

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

Get a published store page › Responses

The resolved page, already-sanitised HTML — render with set:html, never re-sanitise

success
​boolean · required
​StorePagePublic · required

Get the store's saved page document

GET
https://api.wocart.store
/store/page-documents/{surface}
X-Store-API-Key (header)

The store's saved composition for one theme and surface (a page such as home or product, an area such as area:header, or one landing page's lp:<id>), written by Wocart Cloud's editor and read verbatim. data is null when the store has never saved one, or when the saved row is not a document for this surface: the theme then renders its own default. A store that has none is a normal answer, so it is a 200, not a 404.

Get the store's saved page document › path Parameters

surface
​string · pattern: ^[a-z0-9][a-z0-9._:-… · required

Get the store's saved page document › query Parameters

theme
​string · pattern: ^(?=.{1,64}$)[a-z][a…

The requesting theme's key (defineTheme({ key })): its document for the surface. Without it, the most recently saved document for the surface, whichever theme wrote it.

The requesting theme's key (defineTheme({ key })): its document for the surface. Without it, the most recently saved document for the surface, whichever theme wrote it.

Get the store's saved page document › Responses

The saved document, or null when there is none

success
​boolean · required
​PageDocument · required

This page's own composition (its lp:<id> page document) for the requesting theme, written by Wocart Cloud's editor; null when it has none or no theme is named — the theme then renders its landing default.


Get an order's tracking destination

GET
https://api.wocart.store
/store/orders/{id}/tracking
X-Store-API-Key (header)

Which Meta pixel this order belongs to, and which browser event the thank-you page should fire for it.

The thank-you page cannot work this out for itself: it knows the order id and nothing about which landing page the shopper came from, and landing-page attribution is best-effort — an unknown, draft or archived slug leaves the order unattributed. A browser deciding independently would fire at a pixel the Conversions API never mirrors to, and Meta deduplicates per pixel, so that produces two conversions in two ad accounts instead of one.

Returns the decision, not the configuration. event is null when no browser event should fire — either tracking is off, or the merchant's conversion fires further down the funnel (phone confirmation, delivery) from the server only.

Deliberately narrow: nothing about the order itself is returned, and never an access token.

Get an order's tracking destination › path Parameters

id
​string · required

Order UUID

Order UUID

Get an order's tracking destination › Responses

The order's tracking destination

success
​boolean · required
​StoreOrderTracking · required

Find where a shopper's order is

POST
https://api.wocart.store
/store/orders/status
X-Store-API-Key (header)

The order's number and the phone it was placed with prove it is the shopper's, as for a review; a wrong number and a wrong phone both answer 404 ORDER_NOT_FOUND. Attempts are limited per order and per shopper (ORDER_LOOKUP_RATE_LIMITED, with windowSeconds). The answer is what a shopper may know — the step it is at, its lines and total, and the carrier's tracking number once shipped — never the address, the notes or the merchant's own statuses. A POST, so the phone never sits in a URL or a log.

Find where a shopper's order is › Request Body

orderNumber
​string · pattern: ^ORD-\d{8}-\d+$/i · required

The customer-facing order number, as on the thank-you page and the SMS

phone
​string · minLength: 6 · maxLength: 32 · required

The phone the order was placed with, however it is typed

Find where a shopper's order is › Responses

The order's status

success
​boolean · required
​ShopperOrderStatus · required

List store categories

GET
https://api.wocart.store
/store/categories
X-Store-API-Key (header)

Get product categories ordered by position.

List store categories › query Parameters

locale
​string · maxLength: 35

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

List store categories › Responses

200

List of categories

success
​boolean · required
​object[] · required
count
​integer · required

Number of items in data


Get shipping rates

GET
https://api.wocart.store
/store/shipping-rates
X-Store-API-Key (header)

Per-wilaya shipping rates for the order form. Returns wilayas that have a rule in the default shipping profile; absent wilayas should be treated as unknown/unsupported.

Get shipping rates › Responses

200

Shipping rates keyed by wilaya ID (as string)

success
​boolean · required
​object · required

List communes for a wilaya

GET
https://api.wocart.store
/store/communes/{wilayaId}
X-Store-API-Key (header)

Get all communes for a given wilaya. Use the returned id as communeId when submitting an order.

List communes for a wilaya › path Parameters

wilayaId
​integer · min: 1 · max: 58 · required

Wilaya number (1–58).

Wilaya number (1–58).

List communes for a wilaya › Responses

List of communes for the wilaya

success
​boolean · required
​object[] · required
count
​integer · required

Number of items in data


Create store order

POST
https://api.wocart.store
/store/orders
X-Store-API-Key (header)

Submit a customer order from the public storefront. Finds or creates the customer by phone number.

Basket (items): send items to order several products in one go — up to 20 distinct lines, each up to 100 units. Lines with the same product AND variant are merged and their quantities summed. When items is absent the flat productId/quantity fields are used, so existing integrations are unaffected.

Pricing is server-authoritative. pricePerUnit is accepted for UI continuity and never trusted; every line is priced from the catalog row.

All or nothing. If any line cannot be satisfied — insufficient stock, missing SKU — the whole order is refused and nothing is written.

Delivery fee is resolved per basket: a product's own shipping profile overrides the store default, a commune-level override beats the wilaya rule, and a basket spanning two profiles pays the highest applicable rate. Delivery is refused (not silently free) when any product cannot be shipped to the destination.

Offer selection: send offerId to explicitly select the tier the customer chose. It is honoured only if it independently qualifies — reached, and able to give its benefit; otherwise the server picks the highest threshold that qualifies. Trigger quantity counts a product across all its lines, so two variants of one shirt are two shirts.

Buy X Get Y (discountType: "free"): the reward product is appended as a $0 line item. A reward the stock cannot cover makes its offer not qualify: the product falls to its next offer and the order still succeeds. Reward lines never trigger further offers.

Coupon (couponCode): applied after offers, to the paid lines in its scope that no offer applied to; its discount is shared across those lines, so price is net of it, and a free-delivery coupon makes deliveryFee 0. A code that does not apply refuses the whole order with COUPON_NOT_APPLICABLE (reason, with shortBy or startsAt when there is one) — the order is never placed without it. Its uses are counted by the database as the order is inserted, so two orders cannot take the last one.

Free Shipping (discountType: "free_shipping"): the delivery fee is overridden to 0 — reflected in both deliveryFee and total. This applies only when the basket holds a single distinct product; in a multi-product basket free delivery is earned by the store's basket threshold instead, so one cheap promotional item cannot ship an expensive basket for free.

One checkout, one order (checkoutKey): a UUID the shopper's browser stamps on the checkout attempt. Sent again — a double click, a resubmitted form, a retried request — it answers with the order already placed, as it answered the first time, without placing another; for another phone it is refused with CHECKOUT_KEY_IN_USE. Without it, every request places an order.

Multi-unit variant orders: when different variants are selected per unit, send variantSelections — one entry per unit. Identical variants are grouped into a single line and inventory deducts per-variant.

Create store order › query Parameters

locale
​string · maxLength: 35

The language the shopper checked out in (BCP 47, e.g. fr): recorded on the order, and the language its customer messages are written in, when the store publishes it; the primary language otherwise. The Content-Language response header names the one recorded.

The language the shopper checked out in (BCP 47, e.g. fr): recorded on the order, and the language its customer messages are written in, when the store publishes it; the primary language otherwise. The Content-Language response header names the one recorded.

Create store order › Request Body

customerName
​string · minLength: 2 · maxLength: 100 · required
phone
​string · pattern: ^0[567]\d{8}$ · required
wilayaId
​integer · min: 1 · max: 58 · required
communeId
​string · minLength: 1 · required
productId
​string · minLength: 1 · maxLength: 200
productName
​string · minLength: 1 · maxLength: 200
variantId
​string · minLength: 1
variantLabel
​string · maxLength: 100
quantity
​integer · min: 1 · max: 100
Default: 1
offerId
​string | null
​array | null · maxItems: 100
​array | null · minItems: 1 · maxItems: 20
address
​string · maxLength: 300
deliveryType
​string · enum
Enum values:
home
stop_desk
Default: home
pricePerUnit
​number · min: 0
notes
​string · maxLength: 500
email
​string | null · maxLength: 254
​
fbc
​string
fbp
​string
otpToken
​string | null · minLength: 10 · maxLength: 1024
turnstileToken
​string | null · minLength: 1 · maxLength: 2048
landingPageSlug
​string | null · minLength: 1 · maxLength: 60
couponCode
​string | null · maxLength: 64
checkoutKey
​string | null · uuid

Create store order › Responses

Order created

success
​boolean · required
​object · required

Re-price and check a basket — the quote of an order

POST
https://api.wocart.store
/store/cart/validate
X-Store-API-Key (header)

Read-only. Returns what the catalog says about a basket right now, so the cart can show the truth before the shopper commits. Nothing is written and no stock is reserved.

The body names what is being ordered in the order's own fields: a basket (items[]), or one product — productId, productName, quantity, optionally variantId, a variant per unit (variantSelections) and an offer tier (offerId). A product page asks with exactly what its form will post, and the lines are built the same way the order builds them.

Every line comes back with its CURRENT catalog price, the units still available (maxQuantity, null when the product is not stock-tracked), and a blocker when it cannot be ordered as requested:

  • missing: the product no longer exists
  • unlisted: it is no longer on sale (draft, hidden or removed)
  • out_of_stock: fewer units are available than requested

Blocked lines are excluded from subtotal, from offer evaluation and from the free-delivery calculation, so the basket never promises something checkout would refuse.

freeDelivery is subtotal-based and therefore answerable before the shopper types an address: use remaining for a "spend X more" prompt.

Send destination (wilayaId, optional communeId, deliveryType) and the answer carries delivery: the fee and the total the order would charge there, from the same quote the order itself uses — product shipping profiles, commune overrides, the free-delivery threshold and free-shipping offers included. available: false (fee and total null) means the store does not deliver there, and an order to it is refused with DELIVERY_NOT_AVAILABLE. Without destination, there is no delivery field.

Send couponCode and the answer carries coupon: applied (with the discount taken off the lines, each line's share in its discount, and whether it makes delivery free) or refused with the reason the order would be refused for. Send phone once the shopper has typed it, so a coupon for selected customers, or one use per customer, is judged before the order. Without couponCode, coupon is null.

Product names and variant labels come from the catalog, in the language ?locale= asks for (the store's primary when it does not publish that language), announced in Content-Language. The order itself records the catalog's names in the store's primary language.

Re-price and check a basket — the quote of an order › query Parameters

locale
​string · maxLength: 35

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

The language to serve merchant text in (BCP 47, e.g. fr). Served when the store publishes it, the primary language otherwise; the Content-Language response header names the one served. Untranslated fields fall back to the primary one by one.

Re-price and check a basket — the quote of an order › Request Body

productId
​string · minLength: 1 · maxLength: 200
productName
​string · minLength: 1 · maxLength: 200
variantId
​string · minLength: 1
variantLabel
​string · maxLength: 100
quantity
​integer · min: 1 · max: 100
Default: 1
offerId
​string | null
​array | null · maxItems: 100
​array | null · minItems: 1 · maxItems: 20
pricePerUnit
​number · min: 0
​object
couponCode
​string | null · maxLength: 64
phone
​string · maxLength: 32

Re-price and check a basket — the quote of an order › Responses

Basket priced and checked against the live catalog

success
​boolean · required
​object · required

List a product's approved reviews

GET
https://api.wocart.store
/store/reviews
X-Store-API-Key (header)

A product's approved reviews, newest first, with their photos and voice note. Empty when the store turned reviews off.

List a product's approved reviews › query Parameters

productId
​string · minLength: 1 · required

Product ID to fetch reviews for.

Product ID to fetch reviews for.

limit
​integer · min: 1 · max: 50
Default: 20
offset
​integer | null · min: 0
Default: 0

List a product's approved reviews › Responses

200

One page of approved reviews

success
​boolean · required
​object[] · required
count
​integer · required
total
​integer · required

Approved reviews of this product


Submit a review

POST
https://api.wocart.store
/store/reviews
X-Store-API-Key (header)

Proves the purchase again, records the review and answers at once. Its photos and voice note are prepared afterwards (resized, location data removed); visibility says whether it is public now or after the store checks it — the store's choice.

One review per product of an order (409 ORDER_ALREADY_REVIEWED). Without phone (storefronts on @wocart/storefront 1.5) a review is text only, still for a delivered order — deprecated.

Submit a review › Request Body

orderNumber
​string · pattern: ^ORD-\d{8}-\d+$/i · required

The customer-facing order number, as on the thank-you page and the SMS

productId
​string · minLength: 1 · maxLength: 200 · required
rating
​integer · min: 1 · max: 5 · required
phone
​string | null · minLength: 6 · maxLength: 32

The phone the order was placed with. Storefronts on @wocart/storefront 1.5 send none: their reviews are text only, still for a delivered order. Deprecated without it.

title
​string | null · maxLength: 150
body
​string · maxLength: 2000

At least 10 characters, unless a voice note says it

Default:
grant
​string | null · minLength: 1 · maxLength: 2048

The upload grant from /store/reviews/eligibility, when files are sent

uploads
​string[] · maxItems: 8

Upload IDs from /store/reviews/uploads

Submit a review › Responses

Review received

success
​boolean · required
​object · required

Find an order to review

POST
https://api.wocart.store
/store/reviews/eligibility
X-Store-API-Key (header)

Proves the purchase with the order number and the phone it was placed with, and answers what can be reviewed: the order's products the shopper kept (each once), and — when the store takes photos or a voice note — what may be attached and an upload grant for PUT /store/reviews/uploads (30 minutes).

A wrong number and a wrong phone both answer 404 ORDER_NOT_FOUND. An order not delivered yet answers 422 REVIEW_ORDER_NOT_DELIVERED. Attempts are limited per order number (422 REVIEW_RATE_LIMITED). Turnstile is not asked here: it guards checkout.

Find an order to review › Request Body

orderNumber
​string · pattern: ^ORD-\d{8}-\d+$/i · required

The customer-facing order number, as on the thank-you page and the SMS

phone
​string · minLength: 6 · maxLength: 32 · required

The phone the order was placed with, however it is typed

turnstileToken
​string | null · minLength: 1 · maxLength: 2048

Ignored: Turnstile guards checkout, not reviews — the order number and phone are the proof, and attempts are limited per order

Find an order to review › Responses

The order can be reviewed

success
​boolean · required
​object · required

Send a review photo or voice note

PUT
https://api.wocart.store
/store/reviews/uploads
X-Store-API-Key (header)

The file itself as the request body, with the grant from /store/reviews/eligibility in the X-Review-Grant header (and, for a voice note, its length as the recorder reported it in X-Media-Duration-Ms — shown only when the file does not say). Send each file as soon as it is picked; submit the review with the returned uploadIds.

Its kind is read from the file's bytes: a photo (JPEG, PNG, WebP, GIF — shrink it in the browser first, 8 MB at most) or a voice note (WebM, Ogg, M4A, MP3 — as long as the store allows).

Send a review photo or voice note › Request Body

string · binary

Send a review photo or voice note › Responses

Received; kept until the review is submitted (a day at most)

success
​boolean · required
​object · required