Verifiable purchase receipts for agents: record approval and proof. Wallets and escrow (test mode).
Maintain this server? Claim it
Call this server's tools from your browser. Nothing to install.
Optional. 'Bearer <wallet API key>' returned once by open_wallet. Required for get_balance, purchase, create_checkout unless api_key is passed as a tool argument.
Requests go through mcptry because browsers can't call most MCP servers directly. Header values are sent to the server for that request only and are never stored or logged.
Tool list from our last check. Connect live to refresh it.
Attach proof of delivery to a receipt. Requires the edit_token from record_approval. Moves approved to delivered, or to disputed when status is disputed. over_cap is true when actual_amount exceeds the price cap. Does not move money. Same as POST /v1/receipts/:id/proof.
Proof kind. Examples: order_confirmation, tracking, url, hash.
The proof itself: confirmation id, tracking number, URL, or hash.
Secret returned once by record_approval. Required to attach proof.
Receipt id from record_approval (rcpt_…).
Omit to mark an approved receipt delivered. Pass disputed to dispute it.
Amount actually charged. over_cap is true when this is above the price cap.
This tool isn't marked read-only, so it may change something on the server or in an account you connected.
Attach proof of delivery to a receipt. Requires the edit_token from record_approval. Moves approved to delivered, or to disputed when status is disputed. over_cap is true when actual_amount exceeds the price cap. Does not move money. Same as POST /v1/receipts/:id/proof.
| Argument | Type | Description |
|---|---|---|
| type* | string | Proof kind. Examples: order_confirmation, tracking, url, hash. |
| value* | string | The proof itself: confirmation id, tracking number, URL, or hash. |
| status | string | Omit to mark an approved receipt delivered. Pass disputed to dispute it. |
| edit_token* | string | Secret returned once by record_approval. Required to attach proof. |
| receipt_id* | string | Receipt id from record_approval (rcpt_…). |
| actual_amount | any | Amount actually charged. over_cap is true when this is above the price cap. |
{
"type": "object",
"required": [
"receipt_id",
"edit_token",
"type",
"value"
],
"properties": {
"type": {
"type": "string",
"maxLength": 64,
"description": "Proof kind. Examples: order_confirmation, tracking, url, hash."
},
"value": {
"type": "string",
"maxLength": 2000,
"description": "The proof itself: confirmation id, tracking number, URL, or hash."
},
"status": {
"enum": [
"delivered",
"disputed"
],
"type": "string",
"description": "Omit to mark an approved receipt delivered. Pass disputed to dispute it."
},
"edit_token": {
"type": "string",
"description": "Secret returned once by record_approval. Required to attach proof."
},
"receipt_id": {
"type": "string",
"description": "Receipt id from record_approval (rcpt_…)."
},
"actual_amount": {
"anyOf": [
{
"type": "number",
"minimum": 0
},
{
"type": "string",
"maxLength": 40,
"minLength": 1
}
],
"description": "Amount actually charged. over_cap is true when this is above the price cap."
}
},
"additionalProperties": false
}Start a Stripe Checkout credit top-up. Same as POST /v1/wallets/:id/checkout. Returns the checkout url (open that URL; it keeps Stripe's hosted-page fragment). credits is an integer from 500 to 100000 ($5 minimum). Credits are applied only after Stripe reports the session paid. Returns the API error when Stripe is not configured.
| Argument | Type | Description |
|---|---|---|
| api_key | string | Wallet API key (bsk_…). Optional when the MCP client sends Authorization: Bearer. The local stdio process also reads BOTSUPPLY_API_KEY. |
| credits* | integer | Credits to buy. 1 credit = $0.01 USD. Minimum 500 credits ($5). Same limits as POST /v1/wallets/:id/checkout. |
| wallet_id | string | Wallet to credit. Defaults to the wallet that owns the API key. |
{
"type": "object",
"required": [
"credits"
],
"properties": {
"api_key": {
"type": "string",
"description": "Wallet API key (bsk_…). Optional when the MCP client sends Authorization: Bearer. The local stdio process also reads BOTSUPPLY_API_KEY."
},
"credits": {
"type": "integer",
"maximum": 100000,
"minimum": 500,
"description": "Credits to buy. 1 credit = $0.01 USD. Minimum 500 credits ($5). Same limits as POST /v1/wallets/:id/checkout."
},
"wallet_id": {
"type": "string",
"description": "Wallet to credit. Defaults to the wallet that owns the API key."
}
},
"additionalProperties": false
}Hold credits in escrow for a job another agent will do; release when the work is delivered, refund if not. Debits amount_credits from the authenticated payer wallet and marks the job held. payee_wallet_id receives the credits on release. Rejects amount_credits below 1, a payer equal to the payee, a missing or other-mode payee wallet, and insufficient balance. idempotency_key makes a retry return the same job without debiting twice. Same as POST /v1/jobs.
| Argument | Type | Description |
|---|---|---|
| api_key | string | Wallet API key (bsk_…). Optional when the MCP client sends Authorization: Bearer. The local stdio process also reads BOTSUPPLY_API_KEY. |
| description* | string | What the payee is being paid to do. |
| amount_credits* | integer | Credits to debit from the authenticated payer wallet and hold until release or refund. |
| idempotency_key* | string | Caller-chosen key scoped to the payer. A retry with the same key and the same parameters returns the original job and does not debit again. |
| payee_wallet_id* | string | Wallet that receives the credits when the payer releases the job. |
{
"type": "object",
"required": [
"payee_wallet_id",
"amount_credits",
"description",
"idempotency_key"
],
"properties": {
"api_key": {
"type": "string",
"description": "Wallet API key (bsk_…). Optional when the MCP client sends Authorization: Bearer. The local stdio process also reads BOTSUPPLY_API_KEY."
},
"description": {
"type": "string",
"maxLength": 500,
"description": "What the payee is being paid to do."
},
"amount_credits": {
"type": "integer",
"maximum": 1000000000,
"minimum": 1,
"description": "Credits to debit from the authenticated payer wallet and hold until release or refund."
},
"idempotency_key": {
"type": "string",
"maxLength": 128,
"description": "Caller-chosen key scoped to the payer. A retry with the same key and the same parameters returns the original job and does not debit again."
},
"payee_wallet_id": {
"type": "string",
"description": "Wallet that receives the credits when the payer releases the job."
}
},
"additionalProperties": false
}Return the authenticated wallet id and prepaid credit balance. Same as GET /v1/balance. Does not return the API key.
| Argument | Type | Description |
|---|---|---|
| api_key | string | Wallet API key (bsk_…). Optional when the MCP client sends Authorization: Bearer. The local stdio process also reads BOTSUPPLY_API_KEY. |
{
"type": "object",
"properties": {
"api_key": {
"type": "string",
"description": "Wallet API key (bsk_…). Optional when the MCP client sends Authorization: Bearer. The local stdio process also reads BOTSUPPLY_API_KEY."
}
},
"additionalProperties": false
}Return an escrow job's status (held, released, or refunded), the held amount, any release fee, and the payer and payee wallets. The caller must be the payer or the payee. A job from another Stripe mode is not visible. Same as GET /v1/jobs/:id.
| Argument | Type | Description |
|---|---|---|
| job_id* | string | Escrow job id returned by create_job (job_…). |
| api_key | string | Wallet API key (bsk_…). Optional when the MCP client sends Authorization: Bearer. The local stdio process also reads BOTSUPPLY_API_KEY. |
{
"type": "object",
"required": [
"job_id"
],
"properties": {
"job_id": {
"type": "string",
"description": "Escrow job id returned by create_job (job_…)."
},
"api_key": {
"type": "string",
"description": "Wallet API key (bsk_…). Optional when the MCP client sends Authorization: Bearer. The local stdio process also reads BOTSUPPLY_API_KEY."
}
},
"additionalProperties": false
}Read a public purchase receipt: approval, scope, price cap, merchant, proofs, and content hash. No API key. The approver contact and the edit token are not included. Same as GET /v1/receipts/:id.
| Argument | Type | Description |
|---|---|---|
| receipt_id* | string | Public receipt id (rcpt_…). |
{
"type": "object",
"required": [
"receipt_id"
],
"properties": {
"receipt_id": {
"type": "string",
"description": "Public receipt id (rcpt_…)."
}
},
"additionalProperties": false
}List live BotSupply SKUs, credit prices, short descriptions, and what a purchase does not include. Payloads stay behind purchase. recipe.book-table, when listed, is recipe documentation only and does not place a reservation.
No arguments.
{
"type": "object",
"properties": {},
"additionalProperties": false
}Create a wallet and return wallet_id plus api_key once, with balance_credits 0. Same as POST /v1/wallets. This does not look up an existing wallet. Keep the api_key; later tools need it as Authorization: Bearer or as api_key.
| Argument | Type | Description |
|---|---|---|
| label | string | Optional label, 1 to 80 characters. Same field as POST /v1/wallets. |
{
"type": "object",
"properties": {
"label": {
"type": "string",
"description": "Optional label, 1 to 80 characters. Same field as POST /v1/wallets."
}
},
"additionalProperties": false
}Buy one live catalog SKU with prepaid credits. Sends { sku } to POST /v1/purchase and returns that JSON, including the pack or recipe payload. Does not place a reservation. recipe.book-table is documentation the buying agent runs itself. An unknown SKU is rejected. Insufficient balance returns an error and does not deduct credits.
| Argument | Type | Description |
|---|---|---|
| sku* | string | Live catalog SKU. The field name is sku, not sku_id. |
| api_key | string | Wallet API key (bsk_…). Optional when the MCP client sends Authorization: Bearer. The local stdio process also reads BOTSUPPLY_API_KEY. |
{
"type": "object",
"required": [
"sku"
],
"properties": {
"sku": {
"type": "string",
"description": "Live catalog SKU. The field name is sku, not sku_id."
},
"api_key": {
"type": "string",
"description": "Wallet API key (bsk_…). Optional when the MCP client sends Authorization: Bearer. The local stdio process also reads BOTSUPPLY_API_KEY."
}
},
"additionalProperties": false
}Record a human's approval of a purchase on any payment rail. BotSupply does not hold or move the money. Returns receipt_id, a public receipt_url, and an edit_token shown once. No wallet or API key. Rate limited per IP. Same as POST /v1/receipts.
| Argument | Type | Description |
|---|---|---|
| scope* | string | What the human approved, in plain text. |
| agent_id | string | Optional id of the agent that will pay. Not a BotSupply API key. |
| approver* | string | Display name or handle of the human who approved the purchase. |
| agent_name | string | Optional display name of the paying agent. |
| merchant_url | string | Optional http or https URL for the merchant. |
| payment_rail* | string | How the agent will pay. Examples: stripe_link, card, x402, botsupply_wallet. |
| merchant_name* | string | Merchant or seller name. |
| approver_contact | string | Optional email or phone. Stored only as a hash and never shown on the receipt. |
Return held escrow credits to the payer when the work is not delivered or the job is cancelled. The payer or the payee can refund, and only while the job is held. The full hold goes back to the payer; no platform fee is taken. Refunding twice, or refunding after release, is rejected and does not move credits again. Same as POST /v1/jobs/:id/refund.
| Argument | Type | Description |
|---|---|---|
| job_id* | string | Escrow job id returned by create_job (job_…). |
| api_key | string | Wallet API key (bsk_…). Optional when the MCP client sends Authorization: Bearer. The local stdio process also reads BOTSUPPLY_API_KEY. |
{
"type": "object",
"required": [
"job_id"
],
"properties": {
"job_id": {
"type": "string",
"description": "Escrow job id returned by create_job (job_…)."
},
"api_key": {
"type": "string",
"description": "Wallet API key (bsk_…). Optional when the MCP client sends Authorization: Bearer. The local stdio process also reads BOTSUPPLY_API_KEY."
}
},
"additionalProperties": false
}Release held escrow credits to the payee when the work is delivered. Only the payer can release, and only while the job is held. ESCROW_FEE_BPS (default 0) is withheld on release, recorded on the job, and credited to nobody; the payee receives amount_credits minus that fee. Releasing twice, or releasing after a refund, is rejected and does not move credits again. Same as POST /v1/jobs/:id/release.
| Argument | Type | Description |
|---|---|---|
| job_id* | string | Escrow job id returned by create_job (job_…). |
| api_key | string | Wallet API key (bsk_…). Optional when the MCP client sends Authorization: Bearer. The local stdio process also reads BOTSUPPLY_API_KEY. |
{
"type": "object",
"required": [
"job_id"
],
"properties": {
"job_id": {
"type": "string",
"description": "Escrow job id returned by create_job (job_…)."
},
"api_key": {
"type": "string",
"description": "Wallet API key (bsk_…). Optional when the MCP client sends Authorization: Bearer. The local stdio process also reads BOTSUPPLY_API_KEY."
}
},
"additionalProperties": false
}Recompute the receipt hash chain and HMAC signature. valid is true when the stored receipt matches the chain and the server signature. valid is false when a row was altered. Same as GET /v1/receipts/:id/verify.
| Argument | Type | Description |
|---|---|---|
| receipt_id* | string | Public receipt id (rcpt_…). |
{
"type": "object",
"required": [
"receipt_id"
],
"properties": {
"receipt_id": {
"type": "string",
"description": "Public receipt id (rcpt_…)."
}
},
"additionalProperties": false
}| price_cap_amount* |
| any |
| Maximum amount approved. A positive decimal, for example 25 or "19.95". |
| price_cap_currency* | string | Currency code, 3 to 10 letters, for example USD or USDC. |
| external_payment_ref | string | Optional id from the payment rail. BotSupply does not look it up. |
{
"type": "object",
"required": [
"approver",
"merchant_name",
"scope",
"price_cap_amount",
"price_cap_currency",
"payment_rail"
],
"properties": {
"scope": {
"type": "string",
"maxLength": 2000,
"description": "What the human approved, in plain text."
},
"agent_id": {
"type": "string",
"maxLength": 120,
"description": "Optional id of the agent that will pay. Not a BotSupply API key."
},
"approver": {
"type": "string",
"maxLength": 120,
"description": "Display name or handle of the human who approved the purchase."
},
"agent_name": {
"type": "string",
"maxLength": 120,
"description": "Optional display name of the paying agent."
},
"merchant_url": {
"type": "string",
"description": "Optional http or https URL for the merchant."
},
"payment_rail": {
"type": "string",
"maxLength": 64,
"description": "How the agent will pay. Examples: stripe_link, card, x402, botsupply_wallet."
},
"merchant_name": {
"type": "string",
"maxLength": 160,
"description": "Merchant or seller name."
},
"approver_contact": {
"type": "string",
"maxLength": 320,
"description": "Optional email or phone. Stored only as a hash and never shown on the receipt."
},
"price_cap_amount": {
"anyOf": [
{
"type": "number",
"exclusiveMinimum": 0
},
{
"type": "string",
"maxLength": 40,
"minLength": 1
}
],
"description": "Maximum amount approved. A positive decimal, for example 25 or \"19.95\"."
},
"price_cap_currency": {
"type": "string",
"description": "Currency code, 3 to 10 letters, for example USD or USDC."
},
"external_payment_ref": {
"type": "string",
"maxLength": 200,
"description": "Optional id from the payment rail. BotSupply does not look it up."
}
},
"additionalProperties": false
}