Skip to main content

Overview

POST /buy-with-saved-card buys from online merchants without a merchant integration or a browser on your side. You describe what to buy in plain language. You get back questions or a priced cart, and you confirm the exact cart you showed your human. The holder’s saved card pays. Your agent cannot spend the card on its own. Every confirm pauses for the holder to approve the order with their passkey on their own device. Nothing can be charged before a confirm, and a confirm only ever places the cart whose hash it names. The route is free, and no identity verification is needed. Before the first purchase, the holder needs a card saved (save one; GET /get-saved-cards lists it).

The loop

One conversation per purchase, tied together by conversation_id.

1. Ask

Send what the holder wants as ask. If you know where to ship, send delivery_address on this first call. A cart is bound to the address it was shown for, so an address sent after the cart cannot be confirmed against it.
street, city, state (two letters) and zip are required. Retail shipping also needs phone.

2. Answer questions until a cart comes back

While status is needs_input with no cart, relay reply to your human and send their answer back as the next ask with the same conversation_id. Nothing can be charged during this loop.

3. Show the cart

Show the holder the cart from these fields, not from reply. total_cents is the all-in price. approved_ceiling_cents is the most the merchant may charge once final tax and shipping settle. The approval covers that figure, and anything unused is released. To change the cart (“make it two bags”), send another ask; you get a new cart with a new hash. unmatched lists anything asked for that did not make it into the cart, with a reason. catalog carries the last search with each product’s link and photo.

4. Confirm, then hand over the approval

When the holder agrees, send the cart’s hash as confirm:
The confirm pauses for approval and nothing has been charged yet:
Send approval_url to your human and never open it yourself. They approve with their passkey. Then send the same confirm again:
If the second confirm answers in_progress, the order is already being placed for that approval. Do not confirm again. Read GET /get-purchase-conversation until it lists the order.

Slow turns

A turn runs against a live merchant and can take up to two minutes. The call waits about 45 seconds. A turn that finishes in time comes back complete (state: "done"). A slower one comes back as state: "running" with a turn_id:
Poll every few seconds until state is done (same shape as the POST) or failed.

Track the order

It returns every order the conversation placed with its status (confirming, settled, cancelled, failed), the last checkout attempt, and turn_in_progress. Read it before you repeat a confirm whose outcome is unclear: a failed turn, in_progress, or charge_status: "unknown".

Branch on status, never on reply

conflict error codes:

Errors