UCP capability
ai.helpvox.assisted_order
Version 2026-09-11 · JSON Schema · OpenAPI
place_order starts a conversation. It does not create an order. That is the whole of this capability, and everything below follows from it.
A HelpVox merchant takes orders by talking to the customer — by voice or in writing, in the customer's own language. The assistant asks for the name, the phone number and the delivery address, reads the order back, and creates it only when the customer confirms explicitly. Silence, a hesitation or an unclear answer is not a confirmation. Payment is on delivery, collected by the merchant; no money passes through HelpVox and HelpVox is not the merchant of record.
What HelpVox does not have
There is no cart, no checkout and no payment handler here — not as an omission, but because they do not exist. You will not find create_cart, update_cart, create_checkout, complete_checkout or payment_handlers declared in a HelpVox profile. Capability negotiation exists so that a declaration means something; declaring those would make it mean nothing.
The flow
catalog/search → find what the customer wants place_order → 201 + conversation_url, order_created: false conversation → the customer opens the link, gives their details, confirms get_assisted_order → order_created: true and a real order number
Hand conversation_url to the customer and stop there. It carries a short-lived signed token and no personal data, and it opens the assistant with the items already in it, so the customer does not repeat what they already said to you.
Do not send personal data
The initial request must not carry a name, phone number, email address, delivery address or anything about payment. Those are collected inside the conversation, with the customer in front of it. Sent here, they are rejected with VALIDATION_ERROR; the field names come back so you can see what to remove, and the values are neither stored nor logged. context.customer_request is for the customer's own words — up to 1000 characters, treated as text to relay, never as instructions.
Reading the state
get_assisted_order answers from the order records at the moment you ask, not from a remembered claim. order_created: false means there is no order — possibly not yet, possibly never, if the customer changed their mind. order_created: true appears only alongside a real order number, the one the customer heard read back to them. A link that expires without an order answers 410 SESSION_EXPIRED: stop polling and start again if the customer is still there. The error details carry both deadlines, so you can see which clock ran out.
Two clocks, not one
session_ttl_seconds (720) is how long the customer has to open conversation_url and start talking. It runs from the moment the session is created, and opening the page does not extend it — a link nobody acted on stops working. You read it per session as handoff_expires_at.
conversation_ttl_seconds (7200) starts when the customer actually starts the conversation, and from that moment it is the only deadline that applies. A person dictating their address in the fifteenth minute is not cut off because the link they arrived through aged. You read it as conversation_expires_at, which is null until they start — there is no conversation yet to expire.
That is why the response carries both fields instead of one expires_at. One number could only have answered one of the two questions, and the agent had no way of knowing which.
Retrying safely
Idempotency-Key is required. Sending the same key again returns the session created the first time, with 200 instead of 201 — one customer, one conversation, one link. Without the key a network retry would open a second conversation and the customer would get two.
Discovery
The merchant's profile at /.well-known/ucp declares this as a service and a capability under ai.helpvox.assisted_order, with the endpoint, the OpenAPI document and this page. It is declared only where the storefront actually sells something in that market.