The agent door

Your next customer is an agent.

Bubblio puts a door on your product that AI agents can find, knock on, and walk through — with their human's one-tap blessing, and payment on your own Stripe.

agent ⇄ api.bubblio.dev/agent/hub/mcp
> find "image generator"
1. Your platform — door: "your-platform" (door_9f3c21ab04de)
Generate images with AI
actions: generate_image ($1.00), check_free_image
> quote { door: "your-platform", tool: "generate_image",
args: { prompt: "a lighthouse at night" },
agent_key: "bak_7c31…" }
{
"quote_id": "q_e37f09c41b8d4a52b6a1c07d9e52f8a3",
"status": "needs_approval",
"tool": "generate_image",
"args": { "prompt": "a lighthouse at night" },
"price": { "amount_cents": 50, "currency": "usd", "display": "$1.00" },
"payment": { "rails": ["payment_link"], "merchant": "Your platform" },
"approval": { "url": "https://bubblio.dev/a/apr_51c0…", "code": "HV-38K", … },
"relay_script": "Your platform needs your one-time approval — tap …",
}
✓ approved — passkey signed the exact terms · code HV-38K
> confirm { quote_id: "q_e37f09c4…", agent_key: "bak_7c31…" }
{
"quote_id": "q_e37f09c4…", "status": "awaiting_payment", "retry_in": 5,
"payment_challenge": { "type": "payment_link",
"url": "https://checkout.stripe.com/c/pay/cs_live_a1kD…" },
"relay_script": "Your platform needs a one-time payment of $1.00 to run this — pay at …",
}
✓ paid$1.00 checkout settled on your own Stripe
> confirm { quote_id: "q_e37f09c4…", agent_key: "bak_7c31…" }
{
"result": { … },
"receipt": {
"receipt_id": "q_e37f09c41b8d4a52b6a1c07d9e52f8a3",
"tool": "generate_image", "args_hash": "9f2c…",
"tier": "keyed", "approval_id": "apr_51c0…",
"approved_at": "2026-08-16T02:41:07Z",
"price_cents": 50, "currency": "usd",
"payment": { "rail": "payment_link", "amount_cents": 50, "currency": "usd",
"ref": "cs_live_a1kD…", "settled_at": "2026-08-16T02:42:31Z" },
"confirmed_at": "2026-08-16T02:42:44Z",
"outcome": "ok"
}
}

POST https://api.bubblio.dev/agent/hub/mcp — this door is real. Knock.

How it works

Four doors between an agent and your product.

Discover

Agents find your door through one hub connector — find { query } searches every open door — plus a public directory and a product feed. Register once; every discovery surface updates itself.

GET https://api.bubblio.dev/agent/directory

Consent

Actions that need a human get one: the quote returns an approval link the agent relays to their phone. A binding code ties the link to the page, a passkey signs the exact terms, and a mandate checkbox can grant standing consent.

https://bubblio.dev/a/apr_51c0… · code HV-38K

Pay

A quote pins the exact price before anything runs — the quote is the invoice, and an agent never pays more than quoted. Money moves buyer → your own Stripe; a handler that throws is auto-refunded.

"display": "$1.00" — pinned for 10 min (30 with a human or checkout in the loop)

Receipt

Every confirm executes exactly once; confirm the same quote twice and the original receipt replays — the action never re-runs. Approval id, args hash, pinned price: dispute evidence from day one.

"outcome": "ok" · "replayed": true

One line of code

Charge agents like it's a config value.

Declare an action next to its handler, name a price, done. The price is synced to every discovery surface, pinned on every quote, and charged on your own Stripe — Bubblio never touches the money.

$ npm i @bubblio/door

The full integration is four files — here's the whole thing.

export const door = defineDoorActions<DoorUser>({
  actions: {
    generate_image: {
      description: 'Generate an image from a text prompt',
      parameters: [
        { name: 'prompt', type: 'string', required: true },
      ],
      policySuggestion: 'keyed',
      price: '$1.00',  // ← that's it. Pinned on every quote.
      handler: async (args, user) =>
        user ? generateImage(user.id, String(args.prompt))
             : IDENTITY_EXPIRED,
    },
  },
})

Security is the product

The human's passkey signs the exact terms — the action, the arguments, the price — so what they approved is what runs, verbatim. Budgets fail closed: when the ledger can't answer, nothing spends. A quote id alone moves nothing. And money never rests here — payment credentials are transit-only, carried in one signed callback and stored nowhere.

passkey-signed consentexactly-once executionfail-closed budgets128-bit quote idstransit-only tokensWeb Bot Auth verified

The network

Register once. Every door opens.

One hub speaks for every open door — find searches them all, and quote → confirm works on any of them through the same connector.

POST https://api.bubblio.dev/agent/hub/mcp

Doors are open.

No MCP client? Agents also discover doors through the feed /agent/feed.json and llms.txt.

Reading this as an agent? You don't need this page.

Quotes pin the terms. Confirm executes exactly once. Bring your human for the first tap.

Pricing

The door is free. The control room is $19.

The door

$0

  • Agent door, questions tier — about + ask, grounded answers with citations
  • Actions you open, run through quote → confirm, receipted
  • Payments on your own Stripe — Bubblio never holds funds
  • Listed in the public directory and feed
  • The last 7 days of traffic visible in your dashboard
  • Alert emails for the milestones — first agent visit, first confirmed action — and allowance warnings
Open your door

Pro — the control room

$19/mo

  • Everything in the door, plus full traffic history — every visit and the lost-sales funnel back to the day your door opened
  • 1,000 grounded asks a month, one account-wide pool
  • Bring your own Anthropic key to go past it — asks never hard-stop
  • Alert emails when traffic bursts above your door's own normal
  • Early pricing, grandfathered — your price never changes
Start on Pro

Bubblio takes no cut of door payments — money moves buyer → your Stripe. And nothing ever bills on overage: past an allowance the service degrades with an honest notice, never a surprise invoice.

The agents are already at the door.

Open your doorQuickstart — ~10 minutes