# Blizzfull API reference (version 2.4.0) > Read a restaurant's menu, keep it in sync, and put orders into its kitchen. This file is the whole Blizzfull API reference as Markdown: every operation, parameter, request body, response and schema field. It is generated from the API's OpenAPI 3.1.1 document and its JSON Schemas, the same files the human reference is built from. - Human reference: https://blizzfull.com/documentation - OpenAPI 3.1.1: https://apiv2.blizzfull.com/schema/openapi.json (a copy: https://blizzfull.com/developer/openapi.json) - StandardOrder (JSON Schema): https://apiv2.blizzfull.com/schema/standard-order.schema.json (a copy: https://blizzfull.com/developer/standard-order.schema.json; page: https://blizzfull.com/documentation/standard-order) - Menu feed (JSON Schema): https://apiv2.blizzfull.com/schema/menu-feed.schema.json (a copy: https://blizzfull.com/developer/menu-feed.schema.json; page: https://blizzfull.com/documentation/menu-feed) - Blizzfull Menu (import) (JSON Schema): https://apiv2.blizzfull.com/schema/blizzfullMenuSchema.json (a copy: https://blizzfull.com/developer/blizzfullMenuSchema.json; page: https://blizzfull.com/documentation/menu-import) ## Overview The Blizzfull API connects point-of-sale systems, ordering partners and AI agents to Blizzfull restaurants. ### Getting access Every request sends an API user and token. A key belongs to one restaurant (or to a partner's restaurants) and can be narrowed to the calls it needs. Ask your Blizzfull contact for a key; you get a sandbox key first. ### Conventions - **Base URL:** `https://apiv2.blizzfull.com`. - **Envelope:** a successful response is `{"response": ...}`. - **Errors:** a refusal is the HTTP status with `{"response": ""}`. A failure inside the order or menu engine is HTTP 400 with `{"type": "exception", "message": ..., "code": ...}`. - **Money:** orders (StandardOrder) use integer cents. Menus use dollars: numbers when you send them, decimal strings in the feed. - **Time:** ISO 8601, UTC. - **IDs:** Blizzfull's IDs. A menu import uses your own IDs, and Blizzfull remembers the mapping. - **Rate limits:** 1,200 requests a minute per key, 300 of them writes, and 30 order or menu creations every 5 minutes. Over the limit you get HTTP 429 with `Retry-After`. - **Compatibility:** fields are added without notice; ignore the ones you don't use. ### Machine-readable This document and its schemas are served from `https://apiv2.blizzfull.com/schema/`: `openapi.json`, `standard-order.schema.json`, `menu-feed.schema.json` and `blizzfullMenuSchema.json` (JSON Schema 2020-12). ## Authentication Send these headers with every request: - `X-Blizzfull-API-User` (header): Your API user name. - `X-Blizzfull-API-Token` (header): Your API token. Keep it secret; it is shown once. Servers: https://apiv2.blizzfull.com (Production). ## Operations ### Menu Read a restaurant's live menu, or send yours to Blizzfull. #### Get the live menu `GET /items/getFullMenu` · operationId `getMenuFeed` · tags: Menu The restaurant's whole menu as customers see it now: categories, items, sizes, option groups and options, with what is sold out. Everything you need to build an order is here: an item's `id`, its sizes' `id`, and each option group's `linkageID` with its options' `id`. Read it at the start of a session and again when an order is refused for an unknown item; it can be large (a few MB for a big menu). Parameters: - `restaurantID` (query, integer, required): Your key's restaurant. - `locationID` (query, integer, required): Always 1. One of: `1`. Responses: - `200`: The menu. Body (`application/json`): `{ "response": MenuFeed }`. - `401`: The API user or token is missing or wrong. Body (`application/json`): `{ "response": string }`. - Example: `{"response":"Unauthorized"}` - `403`: The key may not make this call, or not for this restaurant or order. Body (`application/json`): `{ "response": string }`. - `429`: Over the rate limit. Wait `Retry-After` seconds. Body (`application/json`): `{ "response": string }`. - Header `Retry-After` (integer): Seconds to wait. Example request (curl): ```bash curl -G "https://apiv2.blizzfull.com/items/getFullMenu" \ -d "restaurantID=$RESTAURANT_ID" \ -d "locationID=1" \ -H "X-Blizzfull-API-User: $BLIZZFULL_API_USER" \ -H "X-Blizzfull-API-Token: $BLIZZFULL_API_TOKEN" ``` Example request (JavaScript): ```js const query = new URLSearchParams({ restaurantID: process.env.RESTAURANT_ID, locationID: '1', }); const res = await fetch(`https://apiv2.blizzfull.com/items/getFullMenu?${query}`, { headers: { 'X-Blizzfull-API-User': process.env.BLIZZFULL_API_USER, 'X-Blizzfull-API-Token': process.env.BLIZZFULL_API_TOKEN, }, }); if (!res.ok) throw new Error(`${res.status}: ${await res.text()}`); const { response } = await res.json(); ``` Example request (Python): ```python import os import requests res = requests.get( "https://apiv2.blizzfull.com/items/getFullMenu", headers={ "X-Blizzfull-API-User": os.environ["BLIZZFULL_API_USER"], "X-Blizzfull-API-Token": os.environ["BLIZZFULL_API_TOKEN"], }, params={"restaurantID": os.environ["RESTAURANT_ID"], "locationID": 1}, timeout=30, ) res.raise_for_status() response = res.json()["response"] ``` Example response (200): ```json { "response": [ { "id": "26900", "name": "Combos", "shortName": "combos", "description": "", "parent": "0", "position": "0", "specialType": null, "active": true, "displayOnly": false, "secret": false, "isMenu": false, "availableTimeData": null, "availableFrom": null, "availableUntil": null, "media": null, "children": null, "items": [ { "id": 166519, "name": "Hungry Combo", "description": "Tenders or wings, a flavor, a side and a drink.", "category": "26900", "categoryName": "Combos", "categoryShortName": "combos", "price": "16.50", "inactive": false, "inactiveEnds": null, "sizeable": false, "sizes": null, "media": null, "spicy": false, "vegetarian": false, "gf": false, "keto": false, "alcoholic": false, "taxExempt": false, "orderTypeRestriction": "", "options": [], "fooditems": [ { "id": 221801, "name": "Hungry Combo", "description": "", "options": [ { "linkageID": "216385", "id": "97001", "componentID": "221801", "title": "Choose a style", "phrase": "", "kitchenname": "", "type": "TYPE_SINGLE_SELECT", "required": true, "position": "1", "defaultIndex": 0, "extraProps": null, "sizeEffects": null, "items": [ { "id": "441415", "name": "6 Tenders", "cost": 0, "default": 0, "unavailableUntil": "0", "position": 1, "media": null, "subOptions": null }, { "id": "441416", "name": "8 Wings", "cost": 0, "default": 0, "unavailableUntil": "0", "position": 2, "media": null, "subOptions": null } ] }, { "linkageID": "216386", "id": "97002", "componentID": "221801", "title": "Choose a flavor", "phrase": "", "kitchenname": "", "type": "TYPE_SINGLE_SELECT", "required": true, "position": "2", "defaultIndex": 0, "extraProps": null, "sizeEffects": null, "items": [ { "id": "441417", "name": "Lemon Pepper", "cost": 0, "default": 0, "unavailableUntil": "0", "position": 1, "media": null, "subOptions": null }, { "id": "441418", "name": "Mango Habanero", "cost": 0.5, "default": 0, "unavailableUntil": "0", "position": 2, "media": null, "subOptions": null } ] } ] } ] } ] } ] } ``` #### Import a menu `POST /menu/import` · operationId `importMenu` · tags: Menu Creates or updates the restaurant's menu from your menu, keyed by your IDs: importing the same IDs again updates the same records. This call does not check the menu against the schema first, and a menu missing a required field can stop part-way. Validate against `blizzfullMenuSchema.json` before you send. A menu sent without any earlier sync replaces the restaurant's menu. Request body (`application/json`, required): a MenuImport document; see the Blizzfull Menu (import) schema below (https://apiv2.blizzfull.com/schema/blizzfullMenuSchema.json). Responses: - `200`: Imported. Body (`application/json`): `{ "response": "success" }`. - `401`: The API user or token is missing or wrong. Body (`application/json`): `{ "response": string }`. - Example: `{"response":"Unauthorized"}` - `403`: The key may not make this call, or not for this restaurant or order. Body (`application/json`): `{ "response": string }`. - `412`: Refused: the message names the field to fix. Body (`application/json`): `{ "response": string }`. - Example: `{"response":"items[0].totalPrice must be the line total in cents"}` - `429`: Over the rate limit. Wait `Retry-After` seconds. Body (`application/json`): `{ "response": string }`. - Header `Retry-After` (integer): Seconds to wait. Example request (curl): ```bash curl "https://apiv2.blizzfull.com/menu/import" \ -H "X-Blizzfull-API-User: $BLIZZFULL_API_USER" \ -H "X-Blizzfull-API-Token: $BLIZZFULL_API_TOKEN" \ -H "Content-Type: application/json" \ -d '{ "categories": [ { "id": "wings", "name": "Wings", "items": [ { "id": "w6", "name": "6 Wings", "price": 9.99, "tags": [ "spicy" ], "groups": [ { "id": "flavors", "required": true } ] } ] } ], "option_groups": [ { "id": "flavors", "name": "Flavor", "type": "TYPE_SINGLE_SELECT", "options": [ { "id": "buffalo", "name": "Buffalo", "price": 0 }, { "id": "lemon-pepper", "name": "Lemon Pepper", "price": 0.5 } ] } ], "sizes": [] }' ``` Example request (JavaScript): ```js const res = await fetch('https://apiv2.blizzfull.com/menu/import', { method: 'POST', headers: { 'X-Blizzfull-API-User': process.env.BLIZZFULL_API_USER, 'X-Blizzfull-API-Token': process.env.BLIZZFULL_API_TOKEN, 'Content-Type': 'application/json', }, body: JSON.stringify({ "categories": [ { "id": "wings", "name": "Wings", "items": [ { "id": "w6", "name": "6 Wings", "price": 9.99, "tags": [ "spicy" ], "groups": [ { "id": "flavors", "required": true } ] } ] } ], "option_groups": [ { "id": "flavors", "name": "Flavor", "type": "TYPE_SINGLE_SELECT", "options": [ { "id": "buffalo", "name": "Buffalo", "price": 0 }, { "id": "lemon-pepper", "name": "Lemon Pepper", "price": 0.5 } ] } ], "sizes": [] }), }); if (!res.ok) throw new Error(`${res.status}: ${await res.text()}`); const { response } = await res.json(); ``` Example request (Python): ```python import os import requests res = requests.post( "https://apiv2.blizzfull.com/menu/import", headers={ "X-Blizzfull-API-User": os.environ["BLIZZFULL_API_USER"], "X-Blizzfull-API-Token": os.environ["BLIZZFULL_API_TOKEN"], }, json={ "categories": [ { "id": "wings", "name": "Wings", "items": [ { "id": "w6", "name": "6 Wings", "price": 9.99, "tags": [ "spicy", ], "groups": [ { "id": "flavors", "required": True, }, ], }, ], }, ], "option_groups": [ { "id": "flavors", "name": "Flavor", "type": "TYPE_SINGLE_SELECT", "options": [ { "id": "buffalo", "name": "Buffalo", "price": 0, }, { "id": "lemon-pepper", "name": "Lemon Pepper", "price": 0.5, }, ], }, ], "sizes": [], }, timeout=30, ) res.raise_for_status() response = res.json()["response"] ``` #### Send your point of sale's menu `POST /menu/importExternalPOSMenu/{posName}` · operationId `importPointOfSaleMenu` · tags: Menu, Point of sale For a point-of-sale partner installed at the restaurant. Checks the menu against the schema, then stores it so the restaurant can map its Blizzfull menu to your items. When the restaurant has made your system its menu's source of truth, the menu is also imported into the live menu. Parameters: - `posName` (path, string, required): Your integration's name at Blizzfull. Example: `"4soft"`. Request body (`application/json`, required): a MenuImport document; see the Blizzfull Menu (import) schema below (https://apiv2.blizzfull.com/schema/blizzfullMenuSchema.json). Responses: - `200`: Stored (and imported, when your system is the menu's source of truth). Body (`application/json`): `{ "response": true }`. - `401`: The API user or token is missing or wrong. Body (`application/json`): `{ "response": string }`. - Example: `{"response":"Unauthorized"}` - `403`: The key may not make this call, or not for this restaurant or order. Body (`application/json`): `{ "response": string }`. - `412`: Refused: the JSON is malformed or doesn't match the schema (`errors` lists each problem), the integration is missing or disabled, or `enforceSyncCompatibility` doesn't match. Body (`application/json`): `{ "type": "error", "message": string, "code": integer, "errors": [{ "property": string, "message": string }] }`. - `429`: Over the rate limit. Wait `Retry-After` seconds. Body (`application/json`): `{ "response": string }`. - Header `Retry-After` (integer): Seconds to wait. Example request (curl): ```bash curl "https://apiv2.blizzfull.com/menu/importExternalPOSMenu/4soft" \ -H "X-Blizzfull-API-User: $BLIZZFULL_API_USER" \ -H "X-Blizzfull-API-Token: $BLIZZFULL_API_TOKEN" \ -H "Content-Type: application/json" \ -d '{ "categories": [ { "id": "wings", "name": "Wings", "items": [ { "id": "w6", "name": "6 Wings", "price": 9.99, "tags": [ "spicy" ], "groups": [ { "id": "flavors", "required": true } ] } ] } ], "option_groups": [ { "id": "flavors", "name": "Flavor", "type": "TYPE_SINGLE_SELECT", "options": [ { "id": "buffalo", "name": "Buffalo", "price": 0 }, { "id": "lemon-pepper", "name": "Lemon Pepper", "price": 0.5 } ] } ], "sizes": [] }' ``` Example request (JavaScript): ```js const res = await fetch('https://apiv2.blizzfull.com/menu/importExternalPOSMenu/4soft', { method: 'POST', headers: { 'X-Blizzfull-API-User': process.env.BLIZZFULL_API_USER, 'X-Blizzfull-API-Token': process.env.BLIZZFULL_API_TOKEN, 'Content-Type': 'application/json', }, body: JSON.stringify({ "categories": [ { "id": "wings", "name": "Wings", "items": [ { "id": "w6", "name": "6 Wings", "price": 9.99, "tags": [ "spicy" ], "groups": [ { "id": "flavors", "required": true } ] } ] } ], "option_groups": [ { "id": "flavors", "name": "Flavor", "type": "TYPE_SINGLE_SELECT", "options": [ { "id": "buffalo", "name": "Buffalo", "price": 0 }, { "id": "lemon-pepper", "name": "Lemon Pepper", "price": 0.5 } ] } ], "sizes": [] }), }); if (!res.ok) throw new Error(`${res.status}: ${await res.text()}`); const { response } = await res.json(); ``` Example request (Python): ```python import os import requests res = requests.post( "https://apiv2.blizzfull.com/menu/importExternalPOSMenu/4soft", headers={ "X-Blizzfull-API-User": os.environ["BLIZZFULL_API_USER"], "X-Blizzfull-API-Token": os.environ["BLIZZFULL_API_TOKEN"], }, json={ "categories": [ { "id": "wings", "name": "Wings", "items": [ { "id": "w6", "name": "6 Wings", "price": 9.99, "tags": [ "spicy", ], "groups": [ { "id": "flavors", "required": True, }, ], }, ], }, ], "option_groups": [ { "id": "flavors", "name": "Flavor", "type": "TYPE_SINGLE_SELECT", "options": [ { "id": "buffalo", "name": "Buffalo", "price": 0, }, { "id": "lemon-pepper", "name": "Lemon Pepper", "price": 0.5, }, ], }, ], "sizes": [], }, timeout=30, ) res.raise_for_status() response = res.json()["response"] ``` ### Orders Place orders into a restaurant and read them back as StandardOrder. #### Place an order `POST /orders` · operationId `createOrder` · tags: Orders Places a pickup order at your key's restaurant, exactly as you send it: your lines, choices and prices are the order. Blizzfull adds tax, submits it to the restaurant like any online order (their tablet, printers and point of sale take it from there), and returns it as a StandardOrder with the order number and total. The customer pays at pickup. The order shows in the restaurant's reports as a phone order. **Retries are safe:** send a `tempID`. If a request times out, send the same body again; an order already placed with that `tempID` in the last 24 hours comes back (HTTP 200) instead of a second one being made. **Building lines:** take each item's `id`, size `id` and choices from the menu feed. `totalPrice` is the line's total in cents (item, size and options, times quantity) and becomes the line's price. Every line needs its `name` and `totalPrice`, so an item the menu no longer has is still recorded as the caller ordered it. Request body (`application/json`, required): A pickup order, in StandardOrder's shape. Only these fields are read. - `tempID` (string): Your reference for this order, 1 to 8 letters, digits, `-` or `_`, unique per order. Makes retries safe. Pattern: `^[A-Za-z0-9_-]{1,8}$`. - `type` (string, required): One of: `"PICKUP"`. - `isFuture` (boolean): True for an order scheduled for `fulfillmentTime`. Leave out for as soon as possible. - `fulfillmentTime` (string (date-time)): When the customer will pick up, with an offset. Read only when `isFuture` is true. - `delayedTime` (integer): Alternative to `isFuture` + `fulfillmentTime`: the pickup time in Unix seconds. 0 means as soon as possible. - `customer` (object, required) - `name` (string): Called out at pickup. Split into first and last name at the first space. - `firstName` (string) - `lastName` (string) - `phone` (string, required): The callback number; at least 10 digits, any formatting. Example: `"(661) 555-0177"`. - `phoneExt` (string) - `email` (string (email)): Optional. When given, the order joins the customer's Blizzfull account for that email; otherwise the account for the phone number. - `note` (string): Instructions for the whole order. - `items` (object[], required): Length: At least 1 item. - `id` (object, required) - `internal` (integer, required): The item's `id` from the menu feed. - `name` (string, required): The item's name, as the caller ordered it. - `quantity` (integer): Default: `1`. Range: At least 1. - `totalPrice` (integer, required): The line total in cents: item, size and options, times quantity. Range: More than 0. - `size` (object) - `id` (object) - `internal` (string | integer): The size's `id` from the menu feed. - `optionSelections` (OptionGroupSelection[]): The caller's choices. List what differs from the menu's defaults. - `note` (string): Instructions for this line. - `discounts` (object[]): Order-level discounts. Their amounts are added up and taken off the order (never below zero); names are not kept. - `amount` (integer, required): Cents. Responses: - `200`: A retry with a `tempID` already used: the order the first request placed. Body (`application/json`): `{ "response": { "order": StandardOrder } }`. - `201`: Placed. Body (`application/json`): `{ "response": { "order": StandardOrder } }`. - `400`: The order engine couldn't take the order, for example a choice that isn't on the item. Body (`application/json`): `{ "type": "exception", "message": string, "code": integer, "trace": null, "request": string }`. - `401`: The API user or token is missing or wrong. Body (`application/json`): `{ "response": string }`. - Example: `{"response":"Unauthorized"}` - `403`: The key may not make this call, or not for this restaurant or order. Body (`application/json`): `{ "response": string }`. - `412`: Refused: the message names the field to fix. Body (`application/json`): `{ "response": string }`. - Example: `{"response":"items[0].totalPrice must be the line total in cents"}` - `429`: Over the rate limit. Wait `Retry-After` seconds. Body (`application/json`): `{ "response": string }`. - Header `Retry-After` (integer): Seconds to wait. Example request (curl): ```bash curl "https://apiv2.blizzfull.com/orders" \ -H "X-Blizzfull-API-User: $BLIZZFULL_API_USER" \ -H "X-Blizzfull-API-Token: $BLIZZFULL_API_TOKEN" \ -H "Content-Type: application/json" \ -d '{ "tempID": "kp1001", "type": "PICKUP", "isFuture": true, "fulfillmentTime": "2026-10-28T19:30:00-07:00", "customer": { "name": "Dana Rivera", "phone": "(661) 555-0177" }, "note": "Called in by phone", "items": [ { "id": { "internal": 166519 }, "name": "Hungry Combo", "quantity": 1, "totalPrice": 1650, "optionSelections": [ { "optionGroupId": "216385", "selections": [ { "optionItemId": "441415", "selected": 1 } ] }, { "optionGroupId": "216386", "selections": [ { "optionItemId": "441417", "selected": 1 } ] } ], "note": "Sauce on the side" } ] }' ``` Example request (JavaScript): ```js const res = await fetch('https://apiv2.blizzfull.com/orders', { method: 'POST', headers: { 'X-Blizzfull-API-User': process.env.BLIZZFULL_API_USER, 'X-Blizzfull-API-Token': process.env.BLIZZFULL_API_TOKEN, 'Content-Type': 'application/json', }, body: JSON.stringify({ "tempID": "kp1001", "type": "PICKUP", "isFuture": true, "fulfillmentTime": "2026-10-28T19:30:00-07:00", "customer": { "name": "Dana Rivera", "phone": "(661) 555-0177" }, "note": "Called in by phone", "items": [ { "id": { "internal": 166519 }, "name": "Hungry Combo", "quantity": 1, "totalPrice": 1650, "optionSelections": [ { "optionGroupId": "216385", "selections": [ { "optionItemId": "441415", "selected": 1 } ] }, { "optionGroupId": "216386", "selections": [ { "optionItemId": "441417", "selected": 1 } ] } ], "note": "Sauce on the side" } ] }), }); if (!res.ok) throw new Error(`${res.status}: ${await res.text()}`); const { response } = await res.json(); ``` Example request (Python): ```python import os import requests res = requests.post( "https://apiv2.blizzfull.com/orders", headers={ "X-Blizzfull-API-User": os.environ["BLIZZFULL_API_USER"], "X-Blizzfull-API-Token": os.environ["BLIZZFULL_API_TOKEN"], }, json={ "tempID": "kp1001", "type": "PICKUP", "isFuture": True, "fulfillmentTime": "2026-10-28T19:30:00-07:00", "customer": { "name": "Dana Rivera", "phone": "(661) 555-0177", }, "note": "Called in by phone", "items": [ { "id": { "internal": 166519, }, "name": "Hungry Combo", "quantity": 1, "totalPrice": 1650, "optionSelections": [ { "optionGroupId": "216385", "selections": [ { "optionItemId": "441415", "selected": 1, }, ], }, { "optionGroupId": "216386", "selections": [ { "optionItemId": "441417", "selected": 1, }, ], }, ], "note": "Sauce on the side", }, ], }, timeout=30, ) res.raise_for_status() response = res.json()["response"] ``` Example response (201): ```json { "response": { "order": { "id": { "internal": "2303306", "external": null }, "status": "SUBMITTED", "type": "PICKUP", "sourcePlatform": "phone", "isFuture": true, "pickupTime": "2026-10-29T02:30:00+00:00", "fulfillmentTime": "2026-10-29T02:30:00+00:00", "taxRate": "8.2500", "processingVia": "manual", "merchant": { "name": "Example Wings", "id": { "internal": "1234", "external": null }, "timezone": "America/Los_Angeles" }, "customer": { "id": "776304", "name": "Dana Rivera", "phone": "+16615550177", "phoneExt": "" }, "items": [ { "quantity": 1, "orderItemID": 1, "id": { "internal": 166519, "external": null }, "name": "Hungry Combo", "note": "Sauce on the side", "unitPrice": 1650, "totalPrice": 1650, "taxRate": 8.25, "optionSelections": [ { "optionGroupId": "216385", "selections": [ { "optionItemId": "441415", "selected": 1 } ] }, { "optionGroupId": "216386", "selections": [ { "optionItemId": "441417", "selected": 1 } ] } ] } ], "totals": { "subtotal": 1650, "tip": 0, "extraCharge": 0, "deliveryFee": 0, "tax": 136, "dspWithheldTax": 0, "total": 1786, "discount": 0, "paid": 0, "balanceOwed": 1786 }, "transactions": [] } } } ``` #### Get an order `GET /orders/{orderId}/getWithRestaurantStd` · operationId `getOrder` · tags: Orders One order as a StandardOrder, with the restaurant details a receipt needs. Use it to check an order's status (`SUBMITTED`, `ACCEPTED`, `FULFILLED`, `CANCELED`) and ready time. Parameters: - `orderId` (path, string, required): The order number (`id.internal`), or `ex-` for a marketplace order. Pattern: `^(ex-)?[1-9][0-9]*$`. Responses: - `200`: The order. Body (`application/json`): - `response` (object, required) - `order` (StandardOrder) - `restaurant` (object): The restaurant's name, address, time zone and receipt settings. - `restaurantID` (string): The Blizzfull restaurant ID. - `name` (string): The restaurant's name. - `streetAddress` (string): Street address. - `city` (string): City. - `state` (string): Two-letter state code. - `zip` (string): ZIP code. - `timeZone` (string): IANA time zone, for showing the order's times locally. - `websiteURL` (string): The restaurant's website. - `receiptLocale` (string | null) - `additionalReceiptLocale` (string | null) - `401`: The API user or token is missing or wrong. Body (`application/json`): `{ "response": string }`. - Example: `{"response":"Unauthorized"}` - `403`: The key may not make this call, or not for this restaurant or order. Body (`application/json`): `{ "response": string }`. - `429`: Over the rate limit. Wait `Retry-After` seconds. Body (`application/json`): `{ "response": string }`. - Header `Retry-After` (integer): Seconds to wait. Example request (curl): ```bash curl "https://apiv2.blizzfull.com/orders/$ORDER_ID/getWithRestaurantStd" \ -H "X-Blizzfull-API-User: $BLIZZFULL_API_USER" \ -H "X-Blizzfull-API-Token: $BLIZZFULL_API_TOKEN" ``` Example request (JavaScript): ```js const res = await fetch(`https://apiv2.blizzfull.com/orders/${process.env.ORDER_ID}/getWithRestaurantStd`, { headers: { 'X-Blizzfull-API-User': process.env.BLIZZFULL_API_USER, 'X-Blizzfull-API-Token': process.env.BLIZZFULL_API_TOKEN, }, }); if (!res.ok) throw new Error(`${res.status}: ${await res.text()}`); const { response } = await res.json(); ``` Example request (Python): ```python import os import requests res = requests.get( f"https://apiv2.blizzfull.com/orders/{os.environ['ORDER_ID']}/getWithRestaurantStd", headers={ "X-Blizzfull-API-User": os.environ["BLIZZFULL_API_USER"], "X-Blizzfull-API-Token": os.environ["BLIZZFULL_API_TOKEN"], }, timeout=30, ) res.raise_for_status() response = res.json()["response"] ``` ### Point of sale For point-of-sale partners: pick up new orders and confirm them. Also in this group: `importPointOfSaleMenu` (POST /menu/importExternalPOSMenu/{posName}), described under Menu. #### Pick up new orders `GET /orders/poll` · operationId `pollOrders` · tags: Point of sale Orders submitted (or accepted) since a time you give, for a point of sale to take into its own ticket flow. Poll every few seconds with the time of the newest order you have. Orders come in Blizzfull's internal order format; with `posToMap`, each is transformed into your integration's ticket format. Parameters: - `orderList` (query, string, required): `,<0|1>`: orders submitted after that time, or with `,1`, orders accepted after it. Example: `"1793142409,0"`. Pattern: `^[0-9]+(,[01])?$`. - `posToMap` (query, string): Your integration's name: returns each order in your ticket format, using the restaurant's item mapping. - `receiveExternalOrders` (query, integer): 1 also returns marketplace orders Blizzfull relays. Requires `posToMap`. One of: `0`, `1`. - `returnRaw` (query, integer): 1 returns the order list itself, without the `response.orderList.data` wrapping. One of: `0`, `1`. Responses: - `200`: The new orders; `orderList` is absent when there are none. Body (`application/json`): `{ "response": { "orderList": { "data": [object] } } }`. - `401`: The API user or token is missing or wrong. Body (`application/json`): `{ "response": string }`. - Example: `{"response":"Unauthorized"}` - `404`: `posToMap` names an integration the restaurant doesn't have. Body (`application/json`): `{ "response": string }`. - `412`: Refused: the message names the field to fix. Body (`application/json`): `{ "response": string }`. - Example: `{"response":"items[0].totalPrice must be the line total in cents"}` - `429`: Over the rate limit. Wait `Retry-After` seconds. Body (`application/json`): `{ "response": string }`. - Header `Retry-After` (integer): Seconds to wait. Example request (curl): ```bash curl -G "https://apiv2.blizzfull.com/orders/poll" \ -d "orderList=1793142409,0" \ -H "X-Blizzfull-API-User: $BLIZZFULL_API_USER" \ -H "X-Blizzfull-API-Token: $BLIZZFULL_API_TOKEN" ``` Example request (JavaScript): ```js const query = new URLSearchParams({ orderList: '1793142409,0', }); const res = await fetch(`https://apiv2.blizzfull.com/orders/poll?${query}`, { headers: { 'X-Blizzfull-API-User': process.env.BLIZZFULL_API_USER, 'X-Blizzfull-API-Token': process.env.BLIZZFULL_API_TOKEN, }, }); if (!res.ok) throw new Error(`${res.status}: ${await res.text()}`); const { response } = await res.json(); ``` Example request (Python): ```python import os import requests res = requests.get( "https://apiv2.blizzfull.com/orders/poll", headers={ "X-Blizzfull-API-User": os.environ["BLIZZFULL_API_USER"], "X-Blizzfull-API-Token": os.environ["BLIZZFULL_API_TOKEN"], }, params={"orderList": "1793142409,0"}, timeout=30, ) res.raise_for_status() response = res.json()["response"] ``` #### Accept an order `POST /orders/{orderId}/accept` · operationId `acceptOrder` · tags: Point of sale Confirms an order on the restaurant's behalf with a ready time. The customer is told it was accepted, and a delivery order's courier is booked. Parameters: - `orderId` (path, string, required): The order number (`id.internal`), or `ex-` for a marketplace order. Pattern: `^(ex-)?[1-9][0-9]*$`. Request body (`application/x-www-form-urlencoded`): - `readyTime` (integer): Minutes until the order is ready. 0 uses the restaurant's default. - `eta` (string): When a delivery courier should pick up, ISO 8601 UTC. - `busyMode` (integer): 1 turns the restaurant's busy mode on, -1 turns it off, 0 (or left out) leaves it as it is. One of: `-1`, `0`, `1`. - `bypassDelayedTime` (integer): 1 starts a scheduled order now instead of at its scheduled time. One of: `0`, `1`. - `bypassCourier` (integer): 1 accepts a delivery order without booking a courier. One of: `0`, `1`. Responses: - `200`: Accepted. Body (`application/json`): `{ "response": { "accepted": 1, "estimatedReadyTime": integer | string, "readyTimeInputValue": integer | string, "pickupETA": integer | boolean, "lastModified": integer | string, "delivery": object } }`. - `401`: The API user or token is missing or wrong. Body (`application/json`): `{ "response": string }`. - Example: `{"response":"Unauthorized"}` - `403`: The key may not make this call, or not for this restaurant or order. Body (`application/json`): `{ "response": string }`. - `429`: Over the rate limit. Wait `Retry-After` seconds. Body (`application/json`): `{ "response": string }`. - Header `Retry-After` (integer): Seconds to wait. Example request (curl): ```bash curl "https://apiv2.blizzfull.com/orders/$ORDER_ID/accept" \ -H "X-Blizzfull-API-User: $BLIZZFULL_API_USER" \ -H "X-Blizzfull-API-Token: $BLIZZFULL_API_TOKEN" \ --data-urlencode "readyTime=20" ``` Example request (JavaScript): ```js const res = await fetch(`https://apiv2.blizzfull.com/orders/${process.env.ORDER_ID}/accept`, { method: 'POST', headers: { 'X-Blizzfull-API-User': process.env.BLIZZFULL_API_USER, 'X-Blizzfull-API-Token': process.env.BLIZZFULL_API_TOKEN, }, body: new URLSearchParams({ "readyTime": 20 }), }); if (!res.ok) throw new Error(`${res.status}: ${await res.text()}`); const { response } = await res.json(); ``` Example request (Python): ```python import os import requests res = requests.post( f"https://apiv2.blizzfull.com/orders/{os.environ['ORDER_ID']}/accept", headers={ "X-Blizzfull-API-User": os.environ["BLIZZFULL_API_USER"], "X-Blizzfull-API-Token": os.environ["BLIZZFULL_API_TOKEN"], }, data={ "readyTime": 20, }, timeout=30, ) res.raise_for_status() response = res.json()["response"] ``` ## Schemas ### StandardOrder Schema: https://apiv2.blizzfull.com/schema/standard-order.schema.json · JSON Schema 2020-12 · page: https://blizzfull.com/documentation/standard-order One restaurant order in Blizzfull's interchange format. The API returns orders in this shape, the point of sale saves them in it, and marketplace orders arrive in it. Conventions: - Money is integer cents (USD) unless a field says otherwise. `coupons[]` is the one exception: it is internal engine state, in dollars. - Tax rates are percentages: `8.25` means 8.25%. - Times are ISO 8601 strings. Blizzfull's own orders use UTC with a `+00:00` offset; some marketplace orders omit the offset (UTC is implied). An unset time is `0000-00-00T00:00:00+00:00`. - Identifiers are pairs: `internal` is Blizzfull's, `external` is the point of sale's or marketplace's. - New fields may be added at any time. Ignore fields you don't recognise. Used by: POST /orders (response); GET /orders/{orderId}/getWithRestaurantStd (response). #### StandardOrder (the document): object - `id` (Identifier, required): The order. `internal` is the Blizzfull order number as a numeric string (`"2303306"`), or `"ex-"` for a marketplace order Blizzfull relayed. `external` is the marketplace's order ID, if any. - `status` (string, required): Where the order is. `OPEN`: being built, not yet sent to the kitchen. `SUBMITTED`: placed, waiting for the restaurant. `ACCEPTED`: the restaurant confirmed it. `FULFILLED`: closed out. `CANCELED`: voided. One of: `"OPEN"`, `"SUBMITTED"`, `"ACCEPTED"`, `"CANCELED"`, `"FULFILLED"`. - `providerStatus` (string): The marketplace's own status word, unchanged (for example `in_progress`). Empty for Blizzfull orders. - `providerOutcome` (string): A marketplace order's reporting outcome, kept apart from `status` (a marketplace failure still closes as `FULFILLED`). `UNKNOWN` for Blizzfull orders. One of: `"ACTIVE"`, `"COMPLETED"`, `"CANCELED"`, `"FAILED"`, `"UNKNOWN"`. - `currencyCode` (string): Always `USD`. One of: `"USD"`. - `note` (string): The customer's instructions for the whole order. Empty when there are none. - `createdTime` (Timestamp): When the order was started. - `orderedTime` (Timestamp): When the order was placed. - `acceptedTime` (Timestamp): When the restaurant accepted it. Unset until then. - `modifiedTime` (Timestamp): When the order last changed. - `pickupTime` (Timestamp): When the order will be ready. For Blizzfull orders this equals `deliveryTime` and the estimated ready time. - `deliveryTime` (Timestamp): When a delivery order is due. Equals `pickupTime` for Blizzfull orders. - `fulfillmentTime` (Timestamp): The time the customer asked for when `isFuture` is true; otherwise the estimated ready time. - `type` (string | null, required): How the order is fulfilled. `PICKUP` covers take-out and curbside. One of: `"PICKUP"`, `"DELIVERY"`, `"DINE-IN"`, `null`. - `sourceType` (string): The marketplace's own fulfilment type. A marketplace courier delivery arrives as `type: PICKUP` (the courier picks it up) with `sourceType: DELIVERY`. `UNKNOWN` for Blizzfull orders. One of: `"PICKUP"`, `"DELIVERY"`, `"DINE-IN"`, `"UNKNOWN"`. - `isExternal` (boolean): True for a marketplace order Blizzfull relayed rather than took. - `isTest` (boolean): True for a test order. Test orders never move real money. - `taxRate` (string | number): The order's tax rate as a percentage. Blizzfull orders send a decimal string with four places (`"8.2500"` is 8.25%); marketplace orders send a number. Older marketplace orders may hold a fraction (`0.1076`). Examples: `"8.2500"`, `10.259`. - `isFuture` (boolean): True when the customer scheduled the order for a later time (see `fulfillmentTime`). Stays true after that time passes. - `table` (string): The dine-in table. Empty for other orders. - `guestCount` (integer): The number of people in a dine-in party. 0 means not recorded. Range: 0 to 255. - `dineinInitTimestamp` (integer): When a dine-in party was seated, in Unix seconds (not ISO 8601). 0 means not recorded. Range: At least 0. - `curbside` (boolean): True when the customer asked to be served at the curb. - `curbsideDetails` (string): The curbside vehicle, as "color make type". Empty otherwise. - `contactFree` (boolean): True when a delivery should be left at the door. - `hasAlcohol` (boolean): True when the order contains alcohol, so ID must be checked on hand-off. - `sourcePlatform` (string): Where the order was placed. For Blizzfull orders: `web`, `app`, `kiosk`, `pos` or `phone` (a phone-ordering partner). For marketplace orders: the marketplace's name. Examples: `"web"`, `"pos"`, `"phone"`. Note: The self-order kiosk is a paid add-on. - `pointsProvider` (string): The loyalty program the points belong to. Currently always `blizzfull`. - `processingVia` (string | null): How the order's payments are processed. `manual`: recorded, not processed (unpaid, cash at the register, pay later). `cash`: cash ordered online. `aggregation` / `blizzfull-pay`: cards processed by Blizzfull. `restaurant-gateway`: the restaurant's own card processor. `restaurant-gateway-cp`: a card reader at the counter. Empty on a few older orders; null for marketplace orders. One of: `"manual"`, `"aggregation"`, `"cash"`, `"restaurant-gateway"`, `"restaurant-gateway-cp"`, `"blizzfull-pay"`, `""`, `null`. - `dailyOrderNumber` (integer | null): The short number called out at the counter, restarting daily. Null when the restaurant doesn't use daily numbers. - `merchant` (Merchant, required): The restaurant location the order belongs to. - `customer` (Customer, required): The person the order is for. - `items` (Item[], required): The order lines, in the order they were added. - `discounts` (Discount[]): Order-level coupons and discounts. Their sum need not equal `totals.discount`: a manual discount from the register has no entry here, and an applied coupon worth $0 still does. - `itemDiscounts` (Discount[]): Item-level discounts, one per discounted line (also listed on the line itself under `items[].discounts`). - `coupons` (object[]): Internal state of Blizzfull's coupon engine, in dollars. Not a stable contract: use `discounts`, `itemDiscounts` and `totals` instead. - `extraCharges` (ExtraCharge[]): Restaurant fees on the order (a service or bag fee), and fees that are themselves taxes. A fee attached to one payment (a card fee) is listed on that payment instead, under `transactions[].extraCharges`. - `delivery` (Delivery | null): Where and how a delivery order goes. Null for other orders. - `totals` (Totals, required): The order's money, in cents. `total = subtotal - discount + deliveryFee + tax + tip + extraCharge`. - `aggregator` (Aggregator | null): The service that relayed a marketplace order. Null for Blizzfull orders. - `transactions` (Transaction[]): Every payment on the order, whatever its status: approved, authorized (held), voided and refunded ones included. Empty when nothing has been paid. #### Timestamp: string ISO 8601 date and time. Blizzfull orders use UTC with a `+00:00` offset; some marketplace orders omit the offset (UTC implied). `0000-00-00T00:00:00+00:00` means not set: treat it as null. Examples: `"2026-10-28T19:30:00+00:00"`, `"0000-00-00T00:00:00+00:00"`. Pattern: `^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}(Z|[+-]\d{2}:\d{2})?$`. #### Identifier: object The same thing's ID in two systems. `internal` is Blizzfull's; `external` is the point of sale's or marketplace's. - `internal` (string | integer | null): Blizzfull's ID. Orders, merchants, sizes and payments use numeric strings; menu items use integers. - `external` (string | null): The other system's ID, or null. #### Merchant: object The restaurant location the order belongs to. - `name` (string, required): The restaurant's name. - `id` (Identifier, required): `internal` is the Blizzfull restaurant ID, a numeric string. - `timezone` (string, required): The restaurant's IANA time zone. Example: `"America/Los_Angeles"`. - `ghostLocationID` (string | null): The virtual brand (ghost kitchen) a marketplace order was placed with. Null otherwise. - `ghostLocationName` (string | null): That virtual brand's name. Null otherwise. #### Customer: object The person the order is for. - `id` (string): The customer's Blizzfull account, as a numeric string. `"5"` is the shared guest account (no account). Empty when the order has no customer. - `name` (string): The name to call out: the name given on the order, else the account's name, email or phone, else `Customer`. - `phone` (string | boolean): The order's callback number in E.164 form (`+16615550177`), or `false` when there is no usable number. Marketplace orders pass the marketplace's number through unchanged. Examples: `"+16615550177"`, `false`. - `phoneExt` (string): A phone extension. Usually empty. - `phoneOptIn` (boolean): Reserved. Currently always false. - `email` (string): The account's email. Accounts created from a phone number carry a placeholder (`6615550177@#`), and guest orders show the guest account's address, so don't treat this as a deliverable address. - `emailOptIn` (boolean): Reserved. Currently always false. #### Item: object One order line: a menu item at a quantity, with its size and options. - `quantity` (integer, required): How many. Range: At least 1. - `orderItemID` (integer | null): The line's number within this order (1, 2, 3…), not a global ID. Null on marketplace orders. - `checkName` (string): The guest's check the line belongs to, as `Guest N`. Empty for the shared check. - `checkNumber` (integer): The guest or seat number. 0 is the shared check. Range: 0 to 255. - `id` (Identifier, required): `internal` is the menu item ID (an integer). 0 is a custom item not on the menu; 1 is a reward with no menu item behind it. Marketplace orders send strings. - `name` (string, required): The line's display name, with the size name already prefixed when there is one. - `translatedName` (string): The name in a second language, on receipts that ask for one. Otherwise empty or absent. - `note` (string): Special instructions for this line. - `category` (Category): The line's menu category. Filled on receipts and point-of-sale tickets; empty in API order responses. - `tags` (string[]): Kitchen routing tags (and `cat-`). Filled on receipts and point-of-sale tickets; empty in API order responses. - `unitPrice` (integer): `totalPrice` divided by `quantity`, rounded to the cent, so it may not multiply back exactly. `totalPrice` is authoritative. - `totalPrice` (integer, required): The line total in cents: the item with its size and options, times quantity, before item discounts. - `customPrice` (integer | null): A line total the cashier typed over the menu price, in cents. Null when the menu price stands. - `taxRate` (number): The line's tax rate as a percentage. 0 for tax-exempt lines. - `discount` (integer): The line's item-level discount in cents. - `size` (Size | []): The size chosen. An empty array (`[]`) when the item has no sizes. Marketplace orders may carry a Size object with null IDs instead. - `discounts` (Discount[]): The line's item-level discounts. - `modifiers` (Modifier[]): The options on the line, ready to print. For the exact choices (with IDs), use `optionSelections`. - `optionSelections` (OptionGroupSelection[] | null): Exactly which options were chosen, by ID. This is the authoritative record of a line's customization, and the shape you send when you create an order. Null when nothing was chosen beyond the defaults, and on receipts. - `pointsUsed` (integer): Loyalty points spent on this line. Range: At least 0. - `loyaltyItemID` (integer): The loyalty reward this line redeems. 0 when it isn't a reward. - `giftCard` (boolean): True when the line sells gift-card value. - `giftCardActivationReference` (string): A signed reference used to activate a physical gift card, never the card number. Empty otherwise. #### OptionGroupSelection: object The choices made in one option group of an item. - `optionGroupId` (string | integer, required): The option group's `linkageID` on this item, from the menu feed (`fooditems[].options[].linkageID`). - `selections` (OptionItemSelection[], required) #### OptionItemSelection: object One option's state. List only what differs from the menu's defaults: an option that is on by default stays on unless you send `selected: 0`. - `optionItemId` (string | integer, required): The option's `id`, from the menu feed (`options[].items[].id`). - `selected` (integer | string, required): 0 turns the option off. 1 or more turns it on: the count for a stepper group, or the level for a variable-amount group (1 light, 2 regular, 3 extra). Usually an integer; a few older orders hold a numeric string. - `included` (boolean): True when the option is one of the group's free (included) choices. Present only when true. - `subOptionSelections` (SubOptionGroupSelection[]): Choices inside the nested groups this option opens (choosing Burger opens Cooking temperature). Options nest two levels at most. #### SubOptionGroupSelection: object The choices made in a nested group. - `optionGroupId` (string | integer, required): The nested group's `id`, from the menu feed (`subOptions[].id`). Nested groups have no `linkageID`. - `selections` (SubOptionItemSelection[], required) #### SubOptionItemSelection: object One option's state in a nested group. It cannot open further groups. - `optionItemId` (string | integer, required): The option's `id` in the nested group. - `selected` (integer | string, required): 0 off; 1 or more on (see `OptionItemSelection.selected`). - `included` (boolean): True when the option is one of the group's free choices. #### Modifier: object One option on a line, as it prints. - `quantity` (integer | string): The selection value per unit of the item (see `OptionItemSelection.selected`). - `id` (Identifier): The option's ID when known. Matched to the option by position, so it can be wrong for items with default options; rely on `optionSelections` for IDs. - `name` (string): Ready to print, prefixes included (`No Onions`, `Extra Ranch`, `2x Ranch`). Don't add the quantity again. - `translatedName` (string): The name in a second language, on receipts that ask for one. - `note` (string): Reserved. Currently always empty. - `group` (ModifierGroup): The option group the choice belongs to. - `food_group` (ModifierGroup): The part of a multi-part item the option belongs to, such as `1st Half` of a pizza. Its name is the item's name when the item has one part. - `unitPrice` (integer): The option's price in cents. 0 on Blizzfull orders, whose option prices are inside the line's `totalPrice`; marketplace orders fill it. - `totalPrice` (integer): `unitPrice` times `quantity`, in cents. 0 on Blizzfull orders. - `taxRate` (number): The option's tax rate as a percentage. - `modifiers` (Modifier[]): Options chosen inside a nested group. One level deep. #### ModifierGroup: object A named group with an ID. - `name` (string): The group's name, when known. Empty in API order responses. - `translatedName` (string) - `id` (Identifier): `internal` is the group's `linkageID` on the item (a string), or null when unknown. #### Category: object The line's menu category. Filled on receipts and point-of-sale tickets; empty in API order responses. - `name` (string) - `translatedName` (string) - `shortName` (string): The category's short name, used to route tickets to printers. - `id` (Identifier): The same thing's ID in two systems. `internal` is Blizzfull's; `external` is the point of sale's or marketplace's. #### Size: object The size variant chosen. - `name` (string): Example: `"Medium 12\""`. - `translatedName` (string) - `id` (Identifier): `internal` is the size ID, a numeric string, or null. - `price` (integer): Reserved. Currently always 0: the size's price is inside the line's `totalPrice`. #### Discount: object A coupon or discount and what it took off, in cents. - `name` (string) - `amount` (integer): What it took off, in cents. Positive. - `id` (Identifier): `internal` is the coupon ID (a numeric string) when it is a Blizzfull coupon. - `description` (string | null) - `itemID` (integer | null): Reserved. Currently always null. - `pointsUsed` (integer | string): Loyalty points spent on the discount. Usually an integer. #### ExtraCharge: object A restaurant fee, or a fee that is itself a tax. - `name` (string) - `id` (Identifier): `internal` is the fee's name. - `amount` (integer): The fee in cents. - `isTax` (boolean): True when the fee is a tax (and counts as tax on receipts). - `taxRate` (number): The percentage the fee is taxed at; 0 when it isn't taxed. - `isPercentage` (integer): Reserved. Currently always 0; `amount` is already in cents. - `taxed` (boolean): True when tax is charged on the fee. #### Totals: object The order's money, in cents. `total = subtotal - discount + deliveryFee + tax + tip + extraCharge`. - `subtotal` (integer, required): The lines' total after item-level discounts. - `tip` (integer): Tips, including tips added after payment. - `extraCharge` (integer): All fees, including those attached to a payment. - `deliveryFee` (integer) - `tax` (integer, required) - `dspWithheldTax` (integer): The part of `tax` a delivery marketplace collected and remits itself. Already included in `tax`. 0 for Blizzfull orders. - `total` (integer, required): What the order costs. - `discount` (integer | null): Order-level discounts only (item-level ones are already out of `subtotal`). Some marketplace orders send null for none. - `paid` (integer, required): What has been paid. 0 for cash ordered online, which is collected on hand-off. - `balanceOwed` (integer, required): What is still owed. 0 when paid in full or canceled; negative when overpaid. #### Delivery: object Where a delivery order goes, and who is taking it. - `address` (string): Street address. - `unit` (string): Apartment, suite or unit. Empty when none. - `city` (string) - `state` (string): Two-letter state code. - `zip` (string) - `full` (string): The whole address on one line, as "address unit city, state zip". - `country` (string): Two-letter country code. `US` for Blizzfull orders. - `courier` (Courier | null): The delivery service taking the order, or null when the restaurant delivers it. - `geo` (Geocode): A point, in decimal degrees. - `notes` (string): Delivery instructions. Usually empty here: instructions are in the order's `note`. - `distance` (string | number): Distance from the restaurant, as a decimal string (`"4.9"`). #### Courier: object The delivery service or driver. - `name` (string): Often the service's name (`Doordash`, `Uber`) rather than a person's. - `phone` (string | boolean): The courier's phone in E.164 form, or `false` when there is none. - `phoneExt` (string) - `email` (string): Reserved. Currently always empty. - `status` (string): Where the courier is. Empty when unknown. One of: `"WAITING"`, `"ACCEPTED"`, `"TRANSIT_TO_MERCHANT"`, `"TRANSIT_TO_CUSTOMER"`, `"DELIVERED"`, `"CANCELLED"`, `""`. - `geo` (Geocode | null): Reserved. Currently always null. - `trackingUrl` (string): A live tracking page, when the service provides one. #### Geocode: object A point, in decimal degrees. - `lat` (number) - `lng` (number) #### Aggregator: object The service that relayed a marketplace order. - `name` (string): Example: `"Stream"`. - `id` (Identifier): `internal` identifies the integration; `external` is the source order's ID. #### Transaction: object One payment. Amounts are cents and stay positive for refunds: `action` and `status` say what happened. - `type` (string): The tender. `CARD` is any card payment; `MANUAL` is one recorded without a processor. One of: `"CASH"`, `"CARD"`, `"PAYPAL"`, `"GIFTCARD"`, `"MANUAL"`, `"OTHER"`. - `amount` (integer): The amount, in cents, tip included. - `tax` (integer): The tax this payment covered. - `tip` (integer): The tip in this payment. - `cashTip` (boolean): True when the tip was paid in cash. - `delivery` (integer): The delivery fee this payment covered. - `discounts` (integer): The discounts applied to this payment. - `processedBy` (string): The processor, lowercased (`finix`, `braintree`, `paypal`, `cash`, `manual`…). Examples: `"finix"`, `"cash"`. - `externalPaymentService` (string): The wallet the card came through. One of: `"none"`, `"applepay"`, `"googlepay"`. - `canChargeAgain` (boolean): True when the card can be charged again for what the order still owes. - `cardBrand` (string | null): The card network, or null. Examples: `"visa"`, `"mastercard"`, `"amex"`, `"discover"`. - `last4` (string | null): The card's last four digits, or null. - `id` (Identifier): `internal` is the payment ID, a numeric string. - `status` (string | null): `AUTHORIZED`: held on the card, not yet captured. `APPROVED`: taken. `VOIDED` / `REFUNDED`: reversed. One of: `"APPROVED"`, `"AUTHORIZED"`, `"VOIDED"`, `"REFUNDED"`, `null`. - `action` (string): Whether the payment took money or returned it. One of: `"sale"`, `"refund"`. - `description` (string | null): A note from the source, such as `Stream transaction`. - `items` (object[]): When a payment covers particular lines (a split check), which lines. - `orderItemID` (integer): The line's `orderItemID`. - `amount` (integer | null): The part of the line paid, in cents; null means all of it. - `itemSplitData` (object | null): For an item or guest split, `{version: 1, allocations: [{orderItemID, amount}]}`. Null otherwise. - `pointsEarned` (string | integer): Loyalty points the payment earned. A numeric string on Blizzfull orders. - `receiptData` (object | array | null): Lines printed on the card receipt. Keys starting with `_` are not for the customer. - `totals` (Totals | null): This payment's money broken down like the order's. Null on marketplace orders. - `extraCharges` (object[]): Fees attached to this payment, such as a card fee. - `name` (string) - `amount` (number): Cents for a `flat` fee; the configured rate for a `percentage` fee. - `calculatedAmountCents` (integer): What the fee came to, in cents. - `type` (string): One of: `"flat"`, `"percentage"`. - `taxed` (boolean) - `isTax` (boolean) Example StandardOrder (the 201 response of POST /orders): ```json { "id": { "internal": "2303306", "external": null }, "status": "SUBMITTED", "type": "PICKUP", "sourcePlatform": "phone", "isFuture": true, "pickupTime": "2026-10-29T02:30:00+00:00", "fulfillmentTime": "2026-10-29T02:30:00+00:00", "taxRate": "8.2500", "processingVia": "manual", "merchant": { "name": "Example Wings", "id": { "internal": "1234", "external": null }, "timezone": "America/Los_Angeles" }, "customer": { "id": "776304", "name": "Dana Rivera", "phone": "+16615550177", "phoneExt": "" }, "items": [ { "quantity": 1, "orderItemID": 1, "id": { "internal": 166519, "external": null }, "name": "Hungry Combo", "note": "Sauce on the side", "unitPrice": 1650, "totalPrice": 1650, "taxRate": 8.25, "optionSelections": [ { "optionGroupId": "216385", "selections": [ { "optionItemId": "441415", "selected": 1 } ] }, { "optionGroupId": "216386", "selections": [ { "optionItemId": "441417", "selected": 1 } ] } ] } ], "totals": { "subtotal": 1650, "tip": 0, "extraCharge": 0, "deliveryFee": 0, "tax": 136, "dspWithheldTax": 0, "total": 1786, "discount": 0, "paid": 0, "balanceOwed": 1786 }, "transactions": [] } ``` ### Menu feed Schema: https://apiv2.blizzfull.com/schema/menu-feed.schema.json · JSON Schema 2020-12 · page: https://blizzfull.com/documentation/menu-feed A restaurant's live menu as Blizzfull serves it from `GET /items/getFullMenu`: its categories, their items, each item's sizes and option groups, and what is available right now. Use it to show the menu and to build orders. An order line names the item's `id`, its size's `id`, and its choices as `optionSelections`, where `optionGroupId` is the option group's `linkageID` on that item and `optionItemId` is the option's `id`. It is a different shape from the menu import format (blizzfullMenuSchema.json): this feed uses Blizzfull's IDs, dollar prices as strings, and the restaurant's current availability. New fields may be added at any time. Ignore fields you don't recognise. Used by: GET /items/getFullMenu (response). #### MenuFeed (the document): Category[] #### Category: object A section of the menu. Items tagged vegan, gluten free, keto or spicy also appear again in the restaurant's matching special category, and items in no category are listed last under `Uncategorized` (id 0). - `id` (string | integer, required): The category's Blizzfull ID. - `name` (string, required) - `shortName` (string): A URL-safe name. - `description` (string) - `parent` (string | integer): The parent category's ID, or 0 for a top-level category. - `position` (string | integer): Display order among its siblings; the array is already sorted by it. - `specialType` (string | null): Set on the restaurant's automatic dietary categories (`gluten-free`, `vegan`, `keto`, `spicy`), whose items also appear in their own categories. Null otherwise. - `active` (boolean): False when the restaurant has hidden the category. - `displayOnly` (boolean): True when the category is shown but can't be ordered from. - `secret` (boolean): True when the category is hidden from the public menu. - `isMenu` (boolean) - `availableTimeData` (integer[][] | null): When the category can be ordered, by weekday from Sunday: seven `[start, end]` pairs in minutes on a clock that starts at 4 AM (240 is 4:00 AM, 1680 is 4:00 AM the next day). Null means whenever the restaurant is open. - `availableFrom` (string | null): First date the category can be ordered, or null. - `availableUntil` (string | null): Last date the category can be ordered, or null. - `media` (Media): Images, or null. - `children` (Category[] | null): Subcategories, with the same fields. Null when there are none. - `items` (Item[], required) #### Item: object Something a customer can order. - `id` (integer, required): The item's Blizzfull ID: an order line's `id.internal`. - `name` (string, required) - `description` (string) - `category` (string): The ID of the item's home category. - `categoryName` (string) - `categoryShortName` (string) - `price` (string, required): The price in dollars, as a decimal string (`"13.99"`). For a sized item, its cheapest size. Example: `"13.99"`. - `inactive` (false | "86" | "nonexistent", required): Whether the item can be ordered now. `false`: available. `"86"`: sold out (until `inactiveEnds`, when set). `"nonexistent"`: removed from the menu. It is never `true`. - `inactiveEnds` (string | null): When a sold-out item comes back, as Unix seconds in a string. `"4294967295"` means until someone turns it back on. Null when available. - `sizeable` (boolean): True when the item comes in sizes. - `sizes` (Size[] | null): The item's sizes, or null when it has none. - `fooditems` (FoodItem[], required): The item's parts. Always one entry, which holds the item's option groups. - `options` (array): Unused; always empty. Option groups are under `fooditems[].options`. - `media` (Media): Images, or null. - `spicy` (boolean) - `vegetarian` (boolean): The vegan badge. - `gf` (boolean): Gluten free. - `keto` (boolean) - `specialty` (boolean) - `alcoholic` (boolean): True when ID must be checked on hand-off. - `taxExempt` (boolean) - `orderTypeRestriction` (string): When set (`take-out`, `delivery`, `for-here`), the item can only be ordered that way. Empty for any. - `appliesToWebApp` (boolean): Offered on the website and app. - `appliesToKiosk` (boolean): Offered at kiosks. Note: The self-order kiosk is a paid add-on. - `appliesToPos` (boolean): Offered at the register. - `calorieRange` (string): As `min-max`; `0-0` when not set. Example: `"500-1200"`. - `customTags` (object[]): The restaurant's own labels for the item. - `text` (string) - `color` (string) - `bgcolor` (string) - `internalOnly` (boolean): True when the label is for staff only: don't show it to customers. - `autoAdd` (boolean) - `stock` (integer) - `posData` (object | null): Data a point-of-sale integration keeps on the item. #### Size: object One size of an item. - `id` (string, required): The size's Blizzfull ID: an order line's `size.id.internal`. - `name` (string, required): Example: `"6 Pcs"`. - `cost` (string, required): The item's whole price in this size, in dollars, as a decimal string. Not an add-on to `price`. Example: `"12.99"`. #### FoodItem: object The item's part that holds its option groups. - `id` (integer) - `name` (string) - `description` (string) - `options` (OptionGroup[]): The item's option groups, in display order. #### OptionGroup: object A set of choices on this item, such as wing flavors. - `linkageID` (string): This group's link to this item. Send it as `optionGroupId` in an order's `optionSelections`. Unique per item; the same group on another item has a different `linkageID`. - `id` (string, required): The option group's own ID, shared by every item it is attached to. - `componentID` (string) - `title` (string, required): The group's name. - `phrase` (string): The prompt shown to customers (`Choose your sauce`). May be empty. - `kitchenname` (string): The name printed for the kitchen. May be empty. - `type` (string, required): How the customer chooses. `TYPE_SINGLE_SELECT`: one option (`selected: 1`). `TYPE_MULTI_SELECT`: any options. `TYPE_UNIT_STEPPER`: a count of each (`selected` is the count). `TYPE_VARIABLE_AMOUNT`: a level of each (`selected` 1 light, 2 regular, 3 extra). One of: `"TYPE_SINGLE_SELECT"`, `"TYPE_MULTI_SELECT"`, `"TYPE_UNIT_STEPPER"`, `"TYPE_VARIABLE_AMOUNT"`. - `required` (boolean): True when the customer must choose. - `position` (string | integer): Display order; the array is already sorted by it. - `defaultIndex` (integer) - `extraProps` (object | null): Limits for this group on this item, when set. - `maxSelectable` (integer | string): The most options a customer may choose. - `minSelectable` (integer | string): The fewest options a customer must choose. - `minRequired` (integer | string) - `maxCombinedAmount` (integer | string): For a stepper, the most units in total. - `amountIncluded` (integer | string): How many choices are included free. - `sizeEffects` (object | null): Option prices that change with the item's size: `items[optionID][sizeID]` is the option's price in dollars for that size. Null when prices don't change by size. - `items` (Option[], required): The options, in display order. #### Option: object One choice in a group. - `id` (string | null, required): The option's Blizzfull ID: send it as `optionItemId`. - `name` (string | null, required) - `cost` (number | string | object, required): What the option adds, in dollars. For a light/regular/extra option, an object with the price per level: `basePrice` (regular), `light`, and `extra` (dollars, or a percentage of `basePrice` such as `"200%"`). As an object: - `basePrice` (number) - `light` (number | string) - `extra` (number | string) - `default` (integer, required): The option's pre-selected value: 0 when not pre-selected, otherwise the count or level. - `unavailableUntil` (string | null): `"0"` when available. Otherwise sold out until this Unix time; `"4294967295"` means until someone turns it back on. - `min` (string): For a stepper: the fewest of this option, as a decimal string. - `max` (string): For a stepper: the most of this option, as a decimal string. - `position` (integer) - `media` (string | null) - `subOptions` (OptionGroup[] | null): Groups that open when this option is chosen, with the same fields as a group (no `linkageID`: in `optionSelections`, a nested group is named by its `id`). Null when there are none. #### Media: object | null Images, or null. - `standard` (object[]) - `id` (string) - `title` (string) - `type` (string): One of: `"image"`. - `source` (string): The image URL. Example MenuFeed (the 200 response of GET /items/getFullMenu): ```json [ { "id": "26900", "name": "Combos", "shortName": "combos", "description": "", "parent": "0", "position": "0", "specialType": null, "active": true, "displayOnly": false, "secret": false, "isMenu": false, "availableTimeData": null, "availableFrom": null, "availableUntil": null, "media": null, "children": null, "items": [ { "id": 166519, "name": "Hungry Combo", "description": "Tenders or wings, a flavor, a side and a drink.", "category": "26900", "categoryName": "Combos", "categoryShortName": "combos", "price": "16.50", "inactive": false, "inactiveEnds": null, "sizeable": false, "sizes": null, "media": null, "spicy": false, "vegetarian": false, "gf": false, "keto": false, "alcoholic": false, "taxExempt": false, "orderTypeRestriction": "", "options": [], "fooditems": [ { "id": 221801, "name": "Hungry Combo", "description": "", "options": [ { "linkageID": "216385", "id": "97001", "componentID": "221801", "title": "Choose a style", "phrase": "", "kitchenname": "", "type": "TYPE_SINGLE_SELECT", "required": true, "position": "1", "defaultIndex": 0, "extraProps": null, "sizeEffects": null, "items": [ { "id": "441415", "name": "6 Tenders", "cost": 0, "default": 0, "unavailableUntil": "0", "position": 1, "media": null, "subOptions": null }, { "id": "441416", "name": "8 Wings", "cost": 0, "default": 0, "unavailableUntil": "0", "position": 2, "media": null, "subOptions": null } ] }, { "linkageID": "216386", "id": "97002", "componentID": "221801", "title": "Choose a flavor", "phrase": "", "kitchenname": "", "type": "TYPE_SINGLE_SELECT", "required": true, "position": "2", "defaultIndex": 0, "extraProps": null, "sizeEffects": null, "items": [ { "id": "441417", "name": "Lemon Pepper", "cost": 0, "default": 0, "unavailableUntil": "0", "position": 1, "media": null, "subOptions": null }, { "id": "441418", "name": "Mango Habanero", "cost": 0.5, "default": 0, "unavailableUntil": "0", "position": 2, "media": null, "subOptions": null } ] } ] } ] } ] } ] ``` ### Blizzfull Menu (import) Schema: https://apiv2.blizzfull.com/schema/blizzfullMenuSchema.json · JSON Schema 2020-12 · page: https://blizzfull.com/documentation/menu-import A whole menu, as a point of sale or partner sends it to Blizzfull to create or update a restaurant's menu. How an import works: - Every ID is yours (the sender's): categories, items, sizes, option groups and options. Blizzfull remembers which of its records each of your IDs became, so importing the same IDs again updates those records in place. Keep IDs stable. An option's ID only needs to be unique within its group. - Arrays are ordered: the menu shows categories, items, groups and options in the order you send them. - Prices are dollars as numbers (`9.99`), not cents. - Option groups are defined once in `option_groups` and attached to items (or whole categories) by ID through `groups`. Only groups that something attaches are imported; the same goes for `sizes`. - Unknown fields are ignored, so you can send extra data. Used by: POST /menu/import (request); POST /menu/importExternalPOSMenu/{posName} (request). #### MenuImport (the document): object - `categories` (category[], required): The menu's categories, in display order. Each holds items and, one level deep, subcategories (`children`). - `option_groups` (option_group[], required): Every option group the menu uses (toppings, sauces, sides, cooking temperatures), defined once and attached to items and categories by ID. Send an empty array when there are none. - `sizes` (size[] | map of size, required): Every size the menu uses (Small, 12", 6 Pcs), defined once and attached to items by ID with a price for each item. Send an empty array when there are none. An object keyed by size ID is also accepted. - `merchant` (object): Optional settings for the restaurant itself rather than its menu. Sending this changes the live restaurant immediately. - `hours` (object): When the restaurant takes orders, separately for delivery and pickup. - `delivery` (store_hours): Ordering hours by weekday, or for one date (`MM/DD`). Each value is a list of `[open, close]` ranges in 24-hour `HH:MM`. A weekday you leave out is closed. - `pickup` (store_hours): Ordering hours by weekday, or for one date (`MM/DD`). Each value is a list of `[open, close]` ranges in 24-hour `HH:MM`. A weekday you leave out is closed. No other keys. - `paused` (boolean): True stops the restaurant taking orders; false resumes. - `custom_maps` (object | array): Extra ID mappings a point-of-sale integration keeps with the menu (for example, how its modifier combinations map to its own items). Stored as given; Blizzfull does not interpret it. - `enforceSyncCompatibility` (integer): Only for `POST /menu/importExternalPOSMenu/{posName}`: the menu-sync version you built against. The current version is `1`; an import is refused if it doesn't match. Ignored by other imports. #### id: integer | string Your ID for the record. Must be stable between imports and must not be 0 or empty. #### images: string | string[] Image URLs: one string, or an array of strings. Each must be absolute, public and point at an image; Blizzfull downloads them during the import, and a URL that is not an image stops the import. Example: `"https://example.com/images/wings.jpg"`. #### store_hours: object Ordering hours by weekday, or for one date (`MM/DD`). Each value is a list of `[open, close]` ranges in 24-hour `HH:MM`. A weekday you leave out is closed. Example: `{"monday":[["11:00","14:30"],["17:00","21:00"]],"12/25":[]}`. - keys matching `^(sunday|monday|tuesday|wednesday|thursday|friday|saturday|\d{2}/\d{2})$` (time_range[]) No other keys. #### time_range: string[] An `[open, close]` pair in 24-hour `HH:MM`. Example: `["11:00","21:30"]`. Length: Exactly 2 items. #### category_hours: object When a category can be ordered, by weekday: `{"monday": [["11:00", "14:45"]]}`. Only the first range of each day is used. Times run from 04:00 to 28:00 (4 AM the next morning), and `["00:00", "00:00"]` closes the day. A weekday you leave out is closed, so `{}` hides the category all week. Leave `hours` out entirely for a category available whenever the restaurant is open. - keys matching `^(sunday|monday|tuesday|wednesday|thursday|friday|saturday)$` (time_range[]) #### category: object A section of the menu holding items, and optionally one level of subcategories. - `id` (id, required): Your ID for the record. Must be stable between imports and must not be 0 or empty. - `name` (string, required) - `description` (string) - `active` (boolean): False hides the category, whatever its hours. Defaults to true. Applied when an existing category is updated; a newly created category is always shown. - `hours` (category_hours): When a category can be ordered, by weekday: `{"monday": [["11:00", "14:45"]]}`. Only the first range of each day is used. Times run from 04:00 to 28:00 (4 AM the next morning), and `["00:00", "00:00"]` closes the day. A weekday you leave out is closed, so `{}` hides the category all week. Leave `hours` out entirely for a category available whenever the restaurant is open. - `imageURL` (images): Image URLs: one string, or an array of strings. Each must be absolute, public and point at an image; Blizzfull downloads them during the import, and a URL that is not an image stops the import. - `imageUrl` (images): Older spelling of `imageURL`, used when `imageURL` is absent. - `groups` (option_group_link[]): Option groups attached to every item in the category, placed before each item's own groups. - `items` (item[]): The category's items, in display order. An item ID that appears in more than one category is imported once, in the last category it appears in. - `children` (category[]): Subcategories. One level only: a subcategory's own `children` are ignored. #### item: object Something a customer can order, with a flat price or a price per size, and the option groups that customize it. - `id` (id, required): Your ID for the record. Must be stable between imports and must not be 0 or empty. - `name` (string, required) - `description` (string | null) - `price` (number, required): The base price in dollars. For a sized item, each size's price is added to this. Example: `12.5`. - `active` (boolean | integer): `true` (or left out): on the menu. `false`: hidden. A Unix timestamp: sold out (86'd) until then. `0`: sold out until turned back on. Examples: `true`, `1793142409`. - `availableDates` (object[]): Limits the item to date windows, in the restaurant's time zone. Both dates are included. Leave it out for an item available every day. Example: `[{"start":"2026-11-26","end":"2026-12-31"}]`. - `start` (string, required): First day, `YYYY-MM-DD`. Pattern: `^\d{4}-\d{2}-\d{2}$`. - `end` (string, required): Last day, `YYYY-MM-DD`. Pattern: `^\d{4}-\d{2}-\d{2}$`. - `tags` (string[]): Dietary and other badges. Recognized: `spicy`, `specialty`, `vegan`, `gf` (gluten free), `keto`, `alcoholic`, and the upper-case forms `HOT`, `SPICY`, `SPECIALTY`, `VEGAN`, `GLUTEN_FREE`. Anything else is ignored, including `vegetarian`: send `vegan`. Example: `["spicy","gf"]`. - `imageURL` (images): Image URLs: one string, or an array of strings. Each must be absolute, public and point at an image; Blizzfull downloads them during the import, and a URL that is not an image stops the import. - `imageUrl` (images): Older spelling of `imageURL`, used when `imageURL` is absent. - `sizes` (item_size[]): The sizes this item comes in, each with its price for this item. The item's displayed price becomes its cheapest size. - `groups` (option_group_link[], required): The option groups that customize this item, in display order. Send an empty array when there are none. - `sku` (string): Your SKU, kept for loyalty-program matching. - `loyaltyMap` (string): Loyalty-program product codes for the item, comma separated. Example: `"478730,478734"`. - `loyaltyTags` (string[] | string): Loyalty-program tags for the item: an array, or one comma-separated string. #### item_size: object One size of this item and what it adds to the item's price. - `id` (id, required): A size from the top-level `sizes`, or a new size defined here with `name`. - `price` (number, required): Dollars added to the item's `price` for this size. With a base price of 5 and a size price of 1, the size costs 6. - `name` (string): The size's name, when it is not in the top-level `sizes`. #### size: object A size, priced per item where items attach it. - `id` (id, required): Your ID for the record. Must be stable between imports and must not be 0 or empty. - `name` (string): Example: `"Large 16\""`. #### option_group: object A set of choices, such as wing flavors or burger toppings. How customers choose depends on `type`. - `id` (id, required): Your ID for the record. Must be stable between imports and must not be 0 or empty. - `name` (string, required) - `type` (string): `TYPE_SINGLE_SELECT`: pick one. `TYPE_MULTI_SELECT`: pick any. `TYPE_UNIT_STEPPER`: pick a quantity of each. `TYPE_VARIABLE_AMOUNT`: pick a level of each (light, regular, extra). When left out, it is inferred: `allow_quantity` above 0 makes a stepper, `force_min` and `force_max` both 1 make a single select, anything else a multi select. One of: `"TYPE_SINGLE_SELECT"`, `"TYPE_MULTI_SELECT"`, `"TYPE_UNIT_STEPPER"`, `"TYPE_VARIABLE_AMOUNT"`. - `allow_quantity` (number): Used only to infer `type` when it is absent: above 0 means a unit stepper. - `force_min` (number): Used only to infer `type` when it is absent. Set limits per item on the group link instead. - `force_max` (number): Used only to infer `type` when it is absent. Set limits per item on the group link instead. - `options` (option[], required): The choices, in display order. Send an empty array for a group with none. #### option: object One choice in an option group, such as Buffalo or Extra Cheese. - `id` (id, required): Your ID for the option, unique within its group. - `name` (string, required) - `price` (number, required): What the option adds, in dollars. May be 0 or negative. - `inactiveEnds` (number): Sold out until this Unix time. Leave it out for an available option. Applied when an existing option is updated, not when it is first created. - `min_units` (integer): For a `TYPE_UNIT_STEPPER` group: the fewest of this option a customer may choose. - `max_units` (integer): For a `TYPE_UNIT_STEPPER` group: the most of this option a customer may choose. - `sub_options` (object[]): Option groups that open when this option is chosen (choosing Burger opens Cooking temperature). Each group must be in `option_groups` and also attached through some item's group link `options[].sub_options`, or it is skipped. - `id` (id, required): An option group's ID. - `sort` (number, deprecated): Ignored: options keep the order they are sent in. #### option_group_link: object Attaches an option group to an item or category, with any rules and defaults for that item. - `id` (id, required): The option group's ID. - `required` (boolean | integer | string): True means the customer must choose from this group. Also accepts 1, "1" and "true". - `force_min` (number): For multi-select groups, the fewest options a customer must choose; for unit steppers, the fewest units. Ignored for single-select and variable-amount groups. - `force_max` (number): For multi-select groups, the most options a customer may choose; for unit steppers, the most units in total. Ignored for single-select and variable-amount groups. - `free_options` (number): How many choices are included free before options start costing extra. Options selected by default don't count. Ignored for single-select groups. - `options` (option_link[]): Per-item settings for particular options of the group: defaults, size prices and nested groups. It does not limit which options appear; every option in the group is offered. #### option_link: object Settings for one option of the group, on this item only. - `id` (id, required): The option's ID within the group. - `default` (integer | boolean): Pre-selects the option: the quantity or level, or true. 0 or false leaves it unselected. A single-select group with no defaults pre-selects its first option. - `sizePriceOverrides` (object[]): This option's price when the item is a given size. - `id` (id, required): The size's ID. - `price` (number | string, required): The option's price in dollars for this size, a percentage of its normal price as a string (`"50%"`), or `-9999` to make the option unavailable in this size. Examples: `1.5`, `"50%"`, `-9999`. - `sub_options` (object[]): Nested groups this option opens on this item, with their defaults. This is what attaches a nested group. - `id` (id, required): The nested option group's ID. - `options` (object[]): Defaults inside the nested group. - `id` (id, required): Your ID for the record. Must be stable between imports and must not be 0 or empty. - `default` (integer | boolean) Example MenuImport (the request body of POST /menu/import): ```json { "categories": [ { "id": "wings", "name": "Wings", "items": [ { "id": "w6", "name": "6 Wings", "price": 9.99, "tags": [ "spicy" ], "groups": [ { "id": "flavors", "required": true } ] } ] } ], "option_groups": [ { "id": "flavors", "name": "Flavor", "type": "TYPE_SINGLE_SELECT", "options": [ { "id": "buffalo", "name": "Buffalo", "price": 0 }, { "id": "lemon-pepper", "name": "Lemon Pepper", "price": 0.5 } ] } ], "sizes": [] } ```