Skip to main content

MCP Server

The OlaClick MCP (Model Context Protocol) Server allows AI agents and MCP-compatible clients to interact with the OlaClick Public API. Connect your AI assistant to OlaClick and query orders, clients, and product sales data using natural language.

What is MCP?​

Model Context Protocol is an open standard that enables AI assistants (like Claude, Cursor, or any MCP-compatible client) to securely interact with external APIs through a standardized interface. Instead of manually crafting API calls, your AI assistant can use OlaClick tools directly.

The MCP server no longer just reads your restaurant's data — it can operate the whole stack: create an order and drive it through its lifecycle (add items, register payments and discounts, apply coupons, change status, cancel it), quote delivery prices before creating an order, run promotions and coupons end to end (create, update, delete), manage webhook subscriptions (create, update, delete), extend the menu (create products and variants, create and update modifiers, sync modifier categories), coordinate logistics (assign a rider, update delivery status), manage clients and their delivery addresses (create, update, list, delete), check food-app store status, and manage connector connections.

Two ways to authenticate​

  • OAuth (recommended) — for Claude.ai, Claude Desktop, Claude Code, ChatGPT, and any MCP client that supports OAuth 2.1. No API key to generate or paste: you sign in with your OlaClick panel account and authorize the connector for the branch you're logged into. Only Admin or Manager users can authorize a connector.
  • API key — for local/stdio setups and clients without OAuth support. You generate a key from the panel and pass it yourself (header or env var).

Both paths reach the same tools and are scoped the same way (see Permissions (scopes)).

Available Tools​

The OlaClick MCP server exposes the tools below, grouped by domain. Kind is derived from the underlying HTTP method: read (GET) never changes data, write (POST/PUT/PATCH) creates or updates it, and destructive (DELETE) removes or cancels something — see Write tools: how they behave.

Orders​

ToolWhat it doesRequired scopeKind
get_ordersRetrieve orders with filters (status, service type, source, dates)orders:readread
get_orderGet a single order by UUID: items, payments, discounts, statusorders:readread
list_tablesList zones and their tables, for a valid table_id on create_orderorders:readread
get_products_soldProduct sales statistics (top sellers, quantities, revenue)orders:readread
create_orderCreate an order (a draft by default)orders:writewrite
update_orderEdit basic fields of an order created through the APIorders:writewrite
update_order_statusAdvance an order's status, including confirming a draftorders:writewrite
cancel_orderCancel an order created through the APIorders:writewrite
add_order_combosAdd one or more items to an orderorders:writewrite
remove_order_comboCancel one item of an orderorders:writedestructive
add_order_paymentRegister a payment against an orderorders:writewrite
remove_order_paymentCancel one payment of an orderorders:writedestructive
add_order_discountApply a manual discount to an orderorders:writewrite
remove_order_discountRemove a discount (or a coupon) from an orderorders:writedestructive
apply_order_couponRedeem a coupon code on an orderorders:writewrite

Promotions​

ToolWhat it doesRequired scopeKind
get_active_promotionsPromotions redeemable right now, filterable by service type and applicabilitypromotions:readread
list_promotionsEvery promotion currently valid (in range, published, redemptions left)promotions:readread
get_promotionGet a single promotion (coupon) by UUIDpromotions:readread
create_promotionCreate a promotion: code, discount, eligibility rulespromotions:writewrite
update_promotionPartially update a promotion (can set a field, not clear it)promotions:writewrite
delete_promotionDelete a promotion — cannot be undonepromotions:writedestructive

Webhooks​

ToolWhat it doesRequired scopeKind
list_webhooksList all webhook configurationswebhooks:readread
get_webhookGet a single webhook configuration by UUIDwebhooks:readread
create_webhookRegister a new webhook URL to receive event notificationswebhooks:writewrite
update_webhookPartially update a webhook configurationwebhooks:writewrite
delete_webhookRemove a webhook subscription — deliveries stop immediatelywebhooks:writedestructive
ToolWhat it doesRequired scopeKind
get_menuMenu catalog: categories, products, prices, availability, imagesmenu:readread
list_categoriesList menu categories (id, name, position, type, visibility)menu:readread
get_categoryGet one category by UUIDmenu:readread
list_productsPaginated product list, optionally filtered by categorymenu:readread
get_productGet one product by UUIDmenu:readread
list_product_variantsList a product's variants (name, price)menu:readread
list_kitchensList the company's kitchensmenu:readread
list_modifier_categoriesList modifier categories with their modifiersmenu:readread
update_productUpdate a product's name or descriptionmenu:writewrite
create_productCreate a product with 1-30 variants (JSON only, no image)menu:writewrite
create_product_variantCreate a variant on an existing productmenu:writewrite
update_product_variantPartially update a product variantmenu:writewrite
sync_product_modifier_categoriesReplace a product's modifier-category associationsmenu:writewrite
create_modifierCreate a modifier in a modifier categorymenu:writewrite
update_modifierPartially update a modifier (e.g. its price)menu:writewrite
update_product_positionMove a product to a new position within its categorymenu:writewrite
update_categoryMove a category to a new position and/or change its visibilitymenu:writewrite

Logistics​

ToolWhat it doesRequired scopeKind
assign_riderAssign or update the delivery rider for an orderlogistics:writewrite
unassign_riderRemove the assigned delivery rider from an orderlogistics:writedestructive
update_delivery_statusUpdate the delivery status of an orderlogistics:writewrite
report_rider_positionReport the rider's current GPS positionlogistics:writewrite

Company & users​

ToolWhat it doesRequired scopeKind
get_companyCompany profile: identity, location, business hours, open-now flagcompanies:readread
list_payment_methodsActive payment methods of the companypayment-methods:readread
list_usersPaginated company users, filterable by role and account statususers:readread
get_clientsList clients with filters (name, phone, status, source, points)clients:readread
get_clientGet a single client by UUID: profile, points, order statsclients:readread
create_clientCreate a new clientclients:writewrite
update_clientPartially update a client's profileclients:writewrite

Addresses​

ToolWhat it doesRequired scopeKind
list_addressesList a client's delivery addressesaddresses:readread
create_addressCreate a delivery address for a clientaddresses:writewrite
update_addressPartially update a delivery addressaddresses:writewrite
delete_addressDelete a delivery addressaddresses:writedestructive

Delivery​

ToolWhat it doesRequired scopeKind
get_delivery_pricingGet the company's delivery pricing configurationorders:readread
get_delivery_quoteGet a delivery price quote for an addressorders:readread

Cash registers​

ToolWhat it doesRequired scopeKind
list_cashiersList the company's cash registers (id, name, default, open or closed); use the id to filter balancescashiers:readread
list_cashier_balancesCash register openings and closings: expected amount, counted amount, surplus/shortage and breakdown by payment method; filter by status, cash register and date rangecashiers:readread
get_cashier_balanceGet a single cash register balance by UUIDcashiers:readread

Dashboard​

ToolWhat it doesRequired scopeKind
get_menu_visits_todayDigital menu visits recorded todayreports:readread
get_menu_performanceDigital menu visits, confirmed carts and created orders over a date range, compared with the previous periodreports:readread
get_menu_conversionThe same metrics as percentages of menu visitsreports:readread

Other​

ToolWhat it doesRequired scopeKind
get_store_statusWhether the store is open on each food-delivery appstores:readread
list_conectionsList connections for the authenticated connectorconections:readread
update_conection_statusAccept or reject a pending connectionconections:writewrite

Write tools: how they behave​

Arguments are the REST endpoint's path parameters and body fields, flattened into one argument list with the same names as the API (e.g. create_order takes service_type, client_id, table_id, ... — the same fields as POST /v1/orders's body; add_order_combos takes id, the order UUID from the path, plus combos, the body).

Local validation runs before any HTTP call: enums, UUID format, numeric bounds and required fields are checked in the MCP server itself, the same way the read tools already validate a page size or a UUID. A malformed call never reaches OlaClick.

create_order and idempotency_key: the REST endpoint requires an Idempotency-Key header. The tool exposes it as an optional idempotency_key argument; when omitted, the server generates one for you. Reuse the same idempotency_key when retrying a failed call — the API replays the original result instead of creating a second order.

MCP annotations: every tool advertises readOnlyHint, destructiveHint and idempotentHint per its kind (see the tables above). MCP clients that honor these hints — Claude Desktop, Cursor, and others — may ask you to confirm before running a destructive tool.

Errors: a failed call returns isError: true with the API's RFC 7807 problem details (type, detail, and a per-field errors[] when applicable) as the tool result, not a thrown exception, so the assistant can read the reason and correct the call (e.g. a missing required field, or a 422 coupon_not_applicable).

Scopes are enforced by the Public API, not by the MCP server: a write tool needs its matching *:write scope on the connecting key (e.g. orders:write for create_order), the same way a read tool needs its *:read scope.

Permissions (scopes)​

Whether you authorize a connector via OAuth or generate an API key, access is broken into the same scopes. Grant only what the assistant needs.

ScopeUnlocks
menu:readRead menu categories and products
menu:writeCreate and update products
orders:readRead orders
orders:writeCreate orders, update order status, items, payments and discounts, and cancel orders
promotions:readRead active promotions and coupons
promotions:writeCreate, update, and delete promotions (coupons)
clients:readRead client list with filters and pagination
clients:writeCreate and update clients
addresses:readRead client delivery addresses
addresses:writeCreate, update, and delete client delivery addresses
reports:readRead reports
webhooks:readList and view webhook configurations
webhooks:writeCreate, update, and delete webhooks
companies:readRead company information
payment-methods:readRead the company payment methods
stores:readRead food-app store open/closed status
users:readRead the company user list with role filter and pagination
fiscal-notes:writeCreate and update fiscal note invoices
logistics:writeAssign riders and update delivery status
cashiers:readRead cash registers and cash register openings and closings

Quick Start​

Prerequisites​

  • An OlaClick panel account (Admin or Manager) for OAuth, or an OlaClick API Key (generated from the restaurant's panel under Integrations > API Keys) for stdio/local clients
  • An MCP-compatible client (Claude Desktop, Claude Code, Cursor, VS Code with Copilot, etc.)

Configuration​

The OlaClick MCP server uses HTTP (SSE) transport. Clients connect to the remote endpoint — no local installation needed.

Client Setup​

Claude.ai / Claude Desktop (OAuth)​

  1. Go to Settings → Connectors → Add custom connector.
  2. Paste the server URL: https://public-api.olaclick.app/mcp.
  3. Click Connect.
  4. Sign in to the OlaClick panel.
  5. Review the requested permissions.
  6. Click Authorize.
  7. You're back in Claude, connected.

Tokens are short-lived and refreshed automatically — you won't be asked to sign in again unless access is revoked. You can revoke the connector at any time from the OlaClick panel.

Claude Code (OAuth)​

claude mcp add --transport http olaclick https://public-api.olaclick.app/mcp

Then run /mcp inside Claude Code and follow the prompt to sign in.

ChatGPT (OAuth)​

ChatGPT connects to remote MCP servers through Developer Mode (Pro, Plus, Business, Enterprise and Education plans, on the web).

  1. Go to Settings → Apps & Connectors → Advanced settings and enable Developer mode.
  2. Back in Apps & Connectors, click Create (or +) to add a connector.
  3. Paste the server URL: https://public-api.olaclick.app/mcp and choose OAuth as the authentication.
  4. Sign in to the OlaClick panel, review the requested permissions and click Authorize.
  5. Start a chat, enable the OlaClick connector in the message composer, and ask away.

Write tools (create order, create product, etc.) are annotated as writes and irreversible ones (cancel an order, delete a promotion or a webhook) as destructive, so ChatGPT can apply its own safeguards; whether it asks you to confirm depends on ChatGPT and your settings. Tokens are short-lived and refreshed automatically.

Cursor​

Add to Cursor

Or add manually to your project's .cursor/mcp.json:

{
"mcpServers": {
"olaclick": {
"url": "https://public-api.olaclick.app/mcp",
"headers": {
"Authorization": "Bearer olk_live_YOUR_KEY_HERE"
}
}
}
}

Claude Desktop​

Add the following to your Claude Desktop configuration file:

macOS: ~/Library/Application Support/Claude/claude_desktop_config.json
Windows: %APPDATA%\Claude\claude_desktop_config.json

{
"mcpServers": {
"olaclick": {
"url": "https://public-api.olaclick.app/mcp",
"headers": {
"Authorization": "Bearer olk_live_YOUR_KEY_HERE"
}
}
}
}

VS Code (Copilot / Kiro)​

Add the following to .vscode/mcp.json or .kiro/settings/mcp.json:

{
"mcpServers": {
"olaclick": {
"url": "https://public-api.olaclick.app/mcp",
"headers": {
"Authorization": "Bearer olk_live_YOUR_KEY_HERE"
}
}
}
}

Remote HTTP (Hosted)​

Connect to the OlaClick MCP server directly via HTTP:

{
"mcpServers": {
"olaclick": {
"url": "https://public-api.olaclick.app/mcp",
"headers": {
"Authorization": "Bearer olk_live_YOUR_KEY_HERE"
}
}
}
}

In HTTP mode, the API key is passed via the Authorization: Bearer header on each connection. No environment variables needed. This is the API-key path — if you authorize via OAuth instead (see above), tools no longer expose an api_key parameter, since the session is already authenticated.

Example Prompts​

Once connected, try asking Claude:

  • "Show me today's orders and their status"
  • "Which products sold the most this week?"
  • "Create a takeaway order for María with 2 cheeseburgers and a Coke, paid in cash"
  • "Add a new product called 'Veggie Wrap' at $8.50 to the Sandwiches category"
  • "List the products in the Drinks category with their prices"
  • "Which promotions are active right now?"

Write actions (creating an order, creating a product) are annotated as writes and irreversible ones as destructive; Claude decides, based on those annotations and your settings, whether to ask you to confirm before running them.

Troubleshooting​

  • "Authorization failed" — make sure you signed in as an Admin or Manager user; other roles can't authorize a connector.
  • "Couldn't reach the MCP server" — check the URL ends in /mcp.
  • Tokens expire — Claude refreshes them automatically; if the connector was revoked, just reconnect.

Tool Reference​

Every tool validates its arguments before calling the API: a wrong type, a malformed UUID or a page size out of range is rejected by the MCP server and never reaches OlaClick.

get_orders​

Retrieve a paginated list of orders with optional filters.

Note: If no start_date is provided, defaults to today's orders.

Parameters:

ParameterTypeRequiredDescription
order_idstringNoUUID or public ID (e.g. PE-1234567890) to get a single order
statusstringNoPENDING, PREPARING, READY, DELIVERED, FINALIZED, CANCELLED
service_typesstringNoDELIVERY, TAKEAWAY, ONSITE, TABLE (comma-separated)
sourcestringNoFilter by source (e.g. web, ifood, rappi, uber)
payment_statusstringNoFilter by payment status (e.g. PAID,PENDING)
payment_method_idsstringNoComma-separated payment method UUIDs
owner_idsstringNoComma-separated owner/cashier UUIDs
rider_idsstringNoComma-separated rider UUIDs
delivered_bystringNoFilter by who delivered (e.g. MERCHANT,IFOOD,PICKER)
delivery_statusstringNoFilter by delivery status
is_scheduledstringNoFilter scheduled orders (true or false)
client_idstringNoFilter by client UUID
public_idstringNoSearch by partial public order ID
cancelation_reasonstringNoFilter by cancelation reason
start_datestringNoFrom date (YYYY-MM-DD)
end_datestringNoUntil date (YYYY-MM-DD)
start_timestringNoFrom time (HH:mm:ss)
end_timestringNoUntil time (HH:mm:ss)
time_typestringNoDate column to filter on (default: pending_at)
timezonestringNoTimezone for date filters (default: company timezone)
pagenumberNoPage number (default: 1)
per_pagenumberNoItems per page (1-100, default: 50)

Example prompt:

"Show me today's pending delivery orders"

Response format:

{
"data": [
{
"id": "9c4f4203-9e2c-403d-88cc-7c0ce9e0f572",
"public_id": "PE-9799906639",
"status": "finalized",
"service_type": "onsite",
"source": "OUTBOUND",
"utm_source": "meta",
"utm_campaign": "combos-julio",
"client": {
"name": "John Doe"
},
"address": {
"city": "Lima",
"area": "Miraflores"
},
"total": 90,
"total_paid": 90,
"total_tips": 0,
"total_discounts": 0,
"delivery_price": 0,
"service_fee_price": 0,
"combos_price": 90,
"created_at": "2026-06-23T18:23:42+00:00",
"updated_at": "2026-06-23T18:56:00+00:00"
}
],
"pagination": {
"current_page": 1,
"per_page": 50,
"total": 12,
"has_more": false
}
}

get_clients​

Retrieve a paginated list of clients with optional filters.

Parameters:

ParameterTypeRequiredDescription
filter_namestringNoPartial match on client name (accent-insensitive)
filter_phone_numberstringNoMatches phone number prefix
filter_country_calling_codestringNoCountry calling code (used with phone_number)
filter_typestringNoFrequency classification (comma-separated): ELITE_BUYER, TOP_BUYER, FREQUENT_BUYER, REPEAT_BUYER, BUYER, NO_BUYER
filter_statusstringNoRecency classification (comma-separated): ACTIVE, INACTIVE, SLEEPING, AT_RISK
filter_sourcestringNochatbot, ecommerce, panel (comma-separated)
filter_available_pointsnumberNoClients with available_points greater than this value
filter_used_pointsnumberNoClients with used_points greater than this value
sort_bystringNoname, phone_number, available_points, used_points, source, total_orders, address
directionstringNoasc or desc
include_addressesbooleanNoInclude client addresses in response
simple_paginatebooleanNoUse simple pagination (faster, no total count)
pagenumberNoPage number (default: 1)
per_pagenumberNoItems per page (1-100, default: 25)

Every client carries two independent classifications, both computed by OlaClick:

  • type — how often they buy, by lifetime order count: ELITE_BUYER (more than 7 orders), TOP_BUYER (5–7), FREQUENT_BUYER (3–4), REPEAT_BUYER (2), BUYER (1), NO_BUYER (0).
  • status — how recently they bought, by days since their last order: ACTIVE (under 16 days), INACTIVE (16–30), SLEEPING (31–91), AT_RISK (over 91 days, or never ordered).

Combine them to build audiences: filter_status=SLEEPING finds customers about to churn, while filter_status=AT_RISK plus a type other than NO_BUYER finds lapsed customers worth winning back.

Example prompt:

"List my top 10 clients sorted by total orders"

Response format:

{
"data": [
{
"id": "9c8e720f-31b1-485a-85fa-0aaf552faaa9",
"name": "John Doe",
"email": "john@example.com",
"phone_number": "3001234567",
"country_calling_code": "57",
"available_points": 150,
"used_points": 0,
"status": "AT_RISK",
"type": "BUYER",
"source": "ecommerce",
"total_orders": 8,
"created_at": "2024-07-19T02:28:48+00:00"
}
],
"pagination": {
"current_page": 1,
"per_page": 25,
"total": 340,
"has_more": true
}
}

create_client​

Create a new client for the authenticated company: name, phone number (with country calling code), and an optional email.

Parameters:

ParameterTypeRequiredDescription
namestringYesClient name, 1-150 characters
phone_numberstringYesNational phone number, without the country code. Digits only
country_calling_codestringYesCountry calling code, without the leading "+", e.g. "51" for Peru
emailstringNoEmail address

Example prompt:

"Create a client named María López, phone 987654321, country code 51"

A duplicate phone number fails with 422 client_already_exists.


update_client​

Partially update a client by UUID: name, phone number, country calling code, or email. Only the fields you send are changed.

Parameters:

ParameterTypeRequiredDescription
idstring (UUID)YesClient UUID
name, phone_number, country_calling_code, email—No**At least one required

Example prompt:

"Update client X's email to maria@example.com"


list_addresses​

List the delivery addresses of one client: street address, coordinates, delivery district (area), and which one is the default. Paginated.

Parameters:

ParameterTypeRequiredDescription
client_idstring (UUID)YesClient UUID to list addresses for
pageintegerNoPage number (default: 1)
per_pageintegerNoItems per page, 1-100

Example prompt:

"List the saved addresses for client 9c8e720f-31b1-485a-85fa-0aaf552faaa9"


create_address​

Create a new delivery address for a client: street address, optional complement, reference, coordinates, and delivery district. Returns the created address, whose id can be used as address_id when creating a DELIVERY order.

Parameters:

ParameterTypeRequiredDescription
client_idstring (UUID)YesClient this address belongs to
addressstringYesStreet address, 1-191 characters
complementstringNoApartment, suite, floor, etc. Max 100 characters
referencestringNoA landmark or note to help find the address. Max 100 characters
latitude, longitudenumberNo**Both or neither, decimal degrees
area_idstring (UUID)NoDelivery district id, for merchants priced by district
defaultbooleanNoWhether this becomes the client's default delivery address

Example prompt:

"Save a new address for client X at Av. Larco 345, Miraflores, lat -12.1211, long -77.0295, and make it the default"


update_address​

Partially update a client delivery address by UUID. Only the fields you send are changed; the owning client cannot be changed. Returns the updated address.

Parameters:

ParameterTypeRequiredDescription
idstring (UUID)YesAddress UUID
address, complement, reference, latitude, longitude, area_id, default—NoSame shape as create_address; latitude/longitude must still be sent together

Example prompt:

"Update address X to set latitude -12.1211 and longitude -77.0295"


delete_address​

Delete a client delivery address by UUID. This cannot be undone.

Parameters:

ParameterTypeRequiredDescription
idstring (UUID)YesAddress UUID

get_delivery_pricing​

Get the authenticated company's delivery pricing configuration: whether delivery is active, the pricing mode, and the mode-specific parameters. Call this first, before get_delivery_quote, to learn which pricing mode applies and which inputs the quote call needs — FIXED and BY_DISTRICT already carry the delivery price in this response, no quote call needed.

No parameters. Mirrors GET /v1/delivery/pricing.

Example prompt:

"How does my restaurant charge for delivery?"


get_delivery_quote​

Resolve the delivery price for one address. Send latitude/longitude for the BY_AREA, BY_DRIVE_DISTANCE, or BY_RANGE pricing modes, or district_id for BY_DISTRICT — call get_delivery_pricing first to know which. A price of 0 with a null area means the address is outside coverage but the merchant still accepts it.

Parameters:

ParameterTypeRequiredDescription
latitude, longitudenumberNo**Both or neither, decimal degrees
district_idstring (UUID)NoDistrict id from get_delivery_pricing's districts[]

Example prompt:

"How much would delivery cost to latitude -34.5955, longitude -58.3930?"


get_menu​

Retrieve the menu catalog: what you sell, at what price, and whether it's available. This is the source for building product catalogs and ad feeds (Meta / Google Shopping).

Note: the menu is not paginated — a large catalog arrives in a single response. Pass category_slug to keep the response to one category. The tool still fetches the full menu and filters it for you.

Parameters:

ParameterTypeRequiredDescription
category_slugstringNoReturn only the category whose slug matches (e.g. combos). Use the slug value this tool returns per category, not the category name or id. An unknown slug returns an error listing the available slugs.
available_onlybooleanNoDrop products that are currently unavailable

Example prompt:

"List my combos with their prices and tell me which ones are out of stock"

Response format:

{
"data": {
"categories": [
{
"id": "026de0fc-85d9-47cd-9c34-627996b6c01c",
"slug": "combos",
"name": "Combos",
"position": 0,
"products": [
{
"id": "9c4f4203-9e2c-403d-88cc-7c0ce9e0f572",
"slug": "combo-classic-smash",
"name": "Combo Classic Smash",
"description": "Smash burger with fries",
"variants": [
{
"id": "6b2f1a04-1c7e-4a2b-9f11-2d8e0b3c4d55",
"name": "Default",
"price": 26,
"currency": "PEN"
}
],
"available": true,
"image_url": "https://assets.olaclick.app/combo-classic-smash.webp"
}
]
}
]
}
}

Prices are in major units (26 means 26.00) with an ISO 4217 currency. image_url is the primary image only. Products with no variants are omitted, since they have no price.


get_products_sold​

Retrieve statistics about the most sold products.

Note: If no start_date is provided, defaults to the last 7 days.

Parameters:

ParameterTypeRequiredDescription
includestringNoGrouping: products, products_modifiers, freehand
show_productsnumberNoLimit to top N products
category_idsstringNoComma-separated category IDs
combo_typestringNoFreehand combo type filter (only when include=freehand)
statusstringNoOrder statuses (e.g. finalized,delivered)
sourcesstringNoOrder sources (e.g. inbound,outbound)
service_typesstringNoService types (e.g. delivery,onsite)
start_datestringNoStart date (YYYY-MM-DD)
end_datestringNoEnd date (YYYY-MM-DD)
timezonestringNoTimezone (default: company timezone)
pagenumberNoPage number (default: 1)
per_pagenumberNoItems per page (1-100, default: 25)

Example prompt:

"What are my top 5 best-selling products this week?"

Response format:

{
"data": [
{
"product_name": "Combo Classic Smash",
"product_quantity": 41,
"average_price": 39,
"total_sales": 1599,
"modifiers": [],
"product_id": "9c4f4203-9e2c-403d-88cc-7c0ce9e0f572",
"variant_id": "9c4f4203-a0ec-45bc-9810-3a8ada0838dd"
}
],
"pagination": {
"current_page": 1,
"per_page": 25,
"total": 45,
"has_more": true
}
}

update_product​

Update a product's name and/or description.

Parameters:

ParameterTypeRequiredDescription
product_idstringYesUUID of the product to update
namestringNo**New product name (max 191 chars)
descriptionstringNo**New product description

**At least one of name or description must be provided.

Example prompt:

"Rename product 9c4f4203-9e2c-403d-88cc-7c0ce9e0f572 to 'Double Smash Burger'"

Response format:

{
"data": {
"id": "9c4f4203-9e2c-403d-88cc-7c0ce9e0f572",
"name": "Double Smash Burger",
"description": "Two smashed beef patties with cheese"
}
}

list_categories​

List the company's menu categories: id, name, position, type, visible. No products, no slug. Use it to browse the catalog structure before listing products.

No parameters. Mirrors GET /v1/menu/categories.

Example prompt:

"Which categories does my menu have, and which ones are hidden?"


get_category​

Get a single menu category by UUID.

ParameterTypeRequiredDescription
idstring (UUID)YesCategory UUID

Mirrors GET /v1/menu/categories/{id}. A non-UUID id is rejected locally.


list_products​

Paginated product list: id, name, description, position, visible, category_id per product. No variants, no slug.

ParameterTypeRequiredDescription
pageintegerNoPage number, 1 or greater (default: 1)
per_pageintegerNoItems per page, 1-100 (default: 20)
category_idstring (UUID)NoOnly products in this category

Mirrors GET /v1/menu/products. A per_page outside 1-100 is rejected locally.

Example prompt:

"List the products in my Combos category"


get_product​

Get a single product by UUID: id, name, description, position, visible, category_id, plus its variants.

ParameterTypeRequiredDescription
idstring (UUID)YesProduct UUID

Mirrors GET /v1/menu/products/{id}.


list_product_variants​

List the variants of one product: id, name, price, original_price, currency, sku, stock, stock_threshold, position per variant. Use it to see the purchasable options of a product returned by get_product or list_products.

ParameterTypeRequiredDescription
idstring (UUID)YesProduct UUID

Mirrors GET /v1/menu/products/{id}/variants.

Example prompt:

"What sizes and prices does product 9c4f4203-9e2c-403d-88cc-7c0ce9e0f572 have?"


list_kitchens​

List the kitchens configured for the company: id, name, default per kitchen. Use it to find valid kitchen ids.

No parameters. Mirrors GET /v1/menu/kitchens.


list_tables​

List the company's zones (rooms) and their tables: each zone has id, name and qrs (the tables/QR points in that zone, each with id, name, nullable description and position). Use it to find valid table_id values when creating a TABLE order.

No parameters. Mirrors GET /v1/tables.


get_company​

Get the profile of the company behind the credential: name, description, logo, public URL, language, currency, location, weekly business hours, and currently_open computed in the company timezone. Requires the companies:read scope.

No parameters. Mirrors GET /v1/company.

Example prompt:

"Is my restaurant open right now, and what are today's hours?"


list_payment_methods​

List the active payment methods of the company: only those enabled for at least one order service type (ONSITE, TABLE, DELIVERY, TAKEAWAY) are returned. Requires the payment-methods:read scope.

No parameters. Mirrors GET /v1/company/payment-methods.


list_users​

Paginated list of the company's users, with role and account status. Requires the users:read scope.

ParameterTypeRequiredDescription
rolestringNoComma-separated roles: admin, manager, waiter, rider, cook, sales, cashier
activebooleanNotrue only active users, false only deactivated users; omit for both
pageintegerNoPage number, 1 or greater (default: 1)
per_pageintegerNoItems per page, 1-100 (default: 20)

Mirrors GET /v1/users, where role and active are sent as filter[role] and filter[active].

Example prompt:

"Which riders do I have active right now?"


create_order​

Create an order and return it. Starts as INITIATED (a draft) unless you send status: PENDING. Add items with add_order_combos, then confirm the draft with update_order_status.

ParameterTypeRequiredDescription
service_typestringYesONSITE, TABLE, DELIVERY, or TAKEAWAY
client_idstring (UUID)NoAn existing client of your company
table_idstring (UUID)NoOnly for TABLE orders; find one with list_tables
address_idstring (UUID)NoOnly for DELIVERY orders
delivery_pricenumberNoOnly for DELIVERY orders
statusstringNoSend PENDING to skip the INITIATED draft
comment, order_title, packaging_price, scheduled_delivery_date—NoOptional order metadata
idempotency_keystringNoReused on retry to avoid a duplicate order; generated when omitted

Example prompt:

"Create a takeaway order for client 9c8e720f-31b1-485a-85fa-0aaf552faaa9"


add_order_combos​

Add one or more items to an order and return it with totals recalculated.

ParameterTypeRequiredDescription
idstring (UUID)YesOrder UUID
combosarrayYesItems to add — each needs variant_id and quantity; modifiers is optional (modifier_id, quantity per modifier)

Example prompt:

"Add 2 Classic Smash combos to order 9c4f4203-9e2c-403d-88cc-7c0ce9e0f572"


add_order_payment​

Register a payment against an order and return it with payment totals recalculated.

ParameterTypeRequiredDescription
idstring (UUID)YesOrder UUID
payment_method_idstring (UUID)YesFrom list_payment_methods
bill_amountnumberYesAmount charged
received_amountnumberNoAmount actually received (cash tendered)
tip_amountnumberNoTip included in this payment

Example prompt:

"Register a cash payment of 45.50 on order X"


apply_order_coupon​

Redeem a coupon code on an order and return it with totals recalculated. The order must have a client attached.

ParameterTypeRequiredDescription
idstring (UUID)YesOrder UUID
codestringYesCoupon code, e.g. VERANO20

Example prompt:

"Apply coupon VERANO20 to order X"


update_order_status​

Change the status of an order and return it. Orders only move forward.

ParameterTypeRequiredDescription
idstring (UUID)YesOrder UUID
statusstringYesNew status, e.g. PENDING, PREPARING, READY, DELIVERED, FINALIZED

Example prompt:

"Move order X to PREPARING"


cancel_order​

Cancel an order created through the API and return it. It must have no active payments — remove them first with remove_order_payment.

ParameterTypeRequiredDescription
idstring (UUID)YesOrder UUID
reasonstringYesCancelation reason code
detailstringNoFree-text detail

Example prompt:

"Cancel order X, the customer changed their mind"


create_promotion​

Create a promotion (coupon): a code, a discount, and eligibility rules.

ParameterTypeRequiredDescription
name, coupon_codestringYesDisplay name and the redeemable code
discount_type, discount_valuestring, numberYese.g. PERCENTAGE + 20, or a fixed amount
minimum_order_amountnumberYesOrder total floor for the coupon to apply
valid_from, valid_untilstring (date)YesValidity window
usage_limitnumberYesTotal redemptions allowed
publishedbooleanYesWhether it's live on the digital menu
promotion_type, products, service_types, audience, usage_limit_per_customer, schedule, terms—NoOptional restrictions and metadata

Example prompt:

"Create a 20% coupon VERANO20 valid until December for delivery only"


update_promotion​

Partially update a promotion. Same fields as create_promotion, all optional — a field can be set but not cleared back to unset.

ParameterTypeRequiredDescription
idstring (UUID)YesPromotion UUID
any create_promotion field—NoOnly the fields you send are changed

Example prompt:

"Extend promotion X's valid_until to January 31"


delete_promotion​

Delete a promotion by UUID. Cannot be undone.

ParameterTypeRequiredDescription
idstring (UUID)YesPromotion UUID

Example prompt:

"Delete the VERANO20 promotion"


create_webhook​

Register a new webhook URL to receive event notifications.

ParameterTypeRequiredDescription
webhook_urlstring (URL)YesHTTPS endpoint that receives events
merchant_idstringYesYour own identifier for this merchant
webhook_headersobjectNoCustom headers sent with every delivery
max_retryintegerNoRetries on failure, 0-10 (default 3)
ack_http_codesarrayNoHTTP codes considered successful (default [200, 201, 202])
event_typesarrayNoEvent types to subscribe to; omit for all events

Example prompt:

"Create a webhook to https://example.com/hooks for merchant store-42"


update_webhook​

Partially update a webhook configuration. Only the fields you send are changed — send is_active: false to pause a webhook without deleting it.

ParameterTypeRequiredDescription
idstring (UUID)YesWebhook UUID
webhook_url, webhook_headers, is_active, max_retry, ack_http_codes, event_types—NoSame shape as create_webhook

Example prompt:

"Pause my webhook X"


delete_webhook​

Remove a webhook subscription by UUID. Deliveries stop immediately.

ParameterTypeRequiredDescription
idstring (UUID)YesWebhook UUID

create_product​

Create a product with 1-30 variants via JSON only (no image upload from the MCP). Prices are decimals, not minor units.

ParameterTypeRequiredDescription
category_id, kitchen_id, namestringYesFrom list_categories / list_kitchens
variantsarrayYes1-30 variants; each needs name, price, original_price, sku
description, visible, modifier_category_ids—NoOptional fields

Example prompt:

"Create a product 'Iced Latte' in the Drinks category, one variant at 12.00"


create_product_variant​

Create a variant on an existing product.

ParameterTypeRequiredDescription
idstring (UUID)YesProduct UUID
name, price, original_price, sku—Yesprice must not exceed original_price
cost, packaging_price, stock, stock_threshold—NoOptional fields

Example prompt:

"Add a Large variant at 15.50 to product X"


update_product_variant​

Partially update a product variant. All fields are optional but at least one must be provided.

ParameterTypeRequiredDescription
id, variantIdstring (UUID)YesProduct and variant UUIDs
name, price, original_price, cost, packaging_price, sku, stock, stock_threshold—No**At least one required

sync_product_modifier_categories​

Replace a product's modifier-category associations, in the given order.

ParameterTypeRequiredDescription
idstring (UUID)YesProduct UUID
modifier_category_idsarray (UUID)YesDistinct UUIDs, from list_modifier_categories; an empty array detaches all

create_modifier​

Create a modifier inside a modifier category. price is what customers pay; it defaults to original_price and must not exceed it.

ParameterTypeRequiredDescription
name, original_price, modifier_category_id, max_limit, visible—YesFrom list_modifier_categories for modifier_category_id
price, sku—Noprice is the charged price; set it below original_price for a discount

Example prompt:

"Add a modifier 'Extra cheese' at 1.50 to the Toppings modifier category"


update_modifier​

Partially update a modifier by its UUID. All fields are optional but at least one must be provided. The main use case is updating a modifier's price.

ParameterTypeRequiredDescription
idstring (UUID)YesModifier UUID
name, price, original_price, sku, max_limit, visible—No**At least one required; price is what customers pay and must not exceed original_price. Sending only original_price also moves price when there is no discount

Example prompt:

"Update the Extra cheese modifier to cost 1.80"


update_product_position​

Move a product to a new position within its category. The product moves to the given position and the other products in that category shift by one to make room.

ParameterTypeRequiredDescription
idstring (UUID)YesProduct UUID
positionintegerYesNew 0-based position; greater than the last existing position fails

update_category​

Partially update a menu category: move it to a new position among sibling categories, and/or change its visibility. At least one field must be provided.

ParameterTypeRequiredDescription
idstring (UUID)YesCategory UUID
positionintegerNo*New 0-based position; greater than the last existing position, or moving a favorites category, fails
visiblebooleanNo*false hides the whole category, including its products, from the menu

*At least one of position/visible required.


assign_rider​

Assign or update the delivery rider for an order.

ParameterTypeRequiredDescription
idstring (UUID)YesOrder UUID
namestringYesRider name
providerstringNoapi (default, external rider) or olaclick
user_idstring (UUID)No**Required when provider: olaclick; must be an active rider-role user
phone_numberstringNoRider phone number

Example prompt:

"Assign rider Marco to order X, phone 555-0100"


update_delivery_status​

Update the delivery status of an order.

ParameterTypeRequiredDescription
idstring (UUID)YesOrder UUID
delivery_statusstringYese.g. ON_THE_WAY_TO_PICK_UP, DELIVERING, DELIVERED

Example prompt:

"Mark order X as out for delivery"

Authentication​

The MCP server supports two authentication methods in HTTP mode:

  • OAuth — Claude.ai, Claude Desktop, Claude Code, and other OAuth-capable clients authenticate via the standard OAuth 2.1 flow (see Two ways to authenticate). No API key involved.

  • API key — clients that don't support OAuth pass an API key via the HTTP Authorization header:

    Authorization: Bearer olk_live_YOUR_KEY_HERE

    The key is passed on the initial HTTP/SSE connection. All tool calls within that session inherit it automatically — no need to pass it per-call.

Example Conversations​

Here are some example prompts you can use once the MCP server is connected:

PromptTool Used
"How many orders did I get today?"get_orders
"Show me all cancelled orders from last week"get_orders
"List delivery orders that are still pending"get_orders
"Which orders came from my Meta campaigns this month?"get_orders
"Who are my most frequent customers?"get_clients
"Find the client with phone number 300..."get_clients
"Which customers are about to churn?"get_clients
"List my menu with prices"get_menu
"Which products are out of stock right now?"get_menu
"What's my best-selling product this month?"get_products_sold
"Show top 10 products for delivery orders"get_products_sold
"Update the description of product X"update_product
"Which categories does my menu have, and which are hidden?"list_categories
"Show me the products in my Combos category"list_categories, then list_products
"What are the details of product X?"get_product
"What sizes and prices does product X come in?"list_product_variants
"Which kitchens do I have set up?"list_kitchens
"Is my restaurant open right now? What are today's hours?"get_company
"Which payment methods do I accept for delivery?"list_payment_methods
"Which riders are active right now?"list_users
"List my managers and cashiers"list_users
"Create a takeaway order for client X with 2 burgers and register a cash payment"create_order, add_order_combos, add_order_payment
"Create a 20% coupon VERANO20 valid until December for delivery only"create_promotion
"Pause my webhook"update_webhook
"Add a Large variant at 15.50 to product X"create_product_variant
"Add a modifier 'Extra cheese' at 1.50 to the Toppings modifier category"create_modifier
"Update the Extra cheese modifier to cost 1.80"update_modifier
"Assign rider Y to order Z"assign_rider
"Mark order Z as out for delivery"update_delivery_status
"Cancel order Z, the customer changed their mind"cancel_order

Security​

  • API keys are never logged or stored by the MCP server
  • All communication uses HTTPS
  • Each user provides their own key via the Authorization header
  • Scopes are enforced by the Public API, not by the MCP server: calling a tool with a key that lacks its scope (e.g. menu:read for get_menu) fails upstream with 403 insufficient_scope
  • Write tools change real data — a created order, an updated promotion, or a deleted webhook is real; there is no dry-run mode at the MCP layer
  • Use a key scoped to only the write scopes an assistant actually needs (e.g. don't hand out orders:write to an assistant that only reads the menu)
  • Destructive tools (backed by DELETE) carry MCP's destructiveHint annotation; clients like Claude Desktop or Cursor may ask you to confirm before running one
  • Treat any API key with a *:write scope as a production credential — store and rotate it the same way you would a database password

Next Steps​