Pay with a Shared Payment Token (MPP-SPT)
This rail settles from a card rather than a crypto balance. Your agent asks the API what the token must authorize, mints a Stripe Shared Payment Token bounded to those values, and hands it back; Stripe redeems it as one card charge. The API never sees the underlying payment method, only the token. Shared Payment Tokens are Stripe’s mechanism for agentic commerce: a limited-scope credential the buyer issues and the seller redeems, capped by amount, currency, recipient, and expiry. You need a token whose role grantsInvoice:Pay — Member, Billing, or
Admin. Creating the experiment additionally needs Experiment:Create,
which Member and Admin carry but Billing does not.
MPP-SPT is offered through the
MCP server, whose
spt_request_for_invoice
and pay_invoice tools drive these two steps.Read the challenge
Create the experiment withX-Adaptyv-Payment-Method: mpp-spt to pin the rail,
confirm the quote, then ask what the token must encode. This call commits to
nothing:
422 means SPT is unavailable in this environment, or the invoice has no
payable amount.
Then call /pay with the method header and no credential. It answers 402 with
the challenge in the WWW-Authenticate response header, and your credential
must echo that challenge back:
Mint the SPT
Mint the SPT againstrecipient_account_id, denominated in currency, capped
at max_amount_cents, and expiring no earlier than expires_at — roughly five
minutes out.
Bound the token to those four values. The API re-checks them against the
challenge before handing the token to Stripe, and Stripe refuses a token that
authorizes less than the amount due, targets another recipient, uses another
currency, or has expired. Bound looser and you are carrying risk for nothing.
The challenge is valid for five minutes. Mint and settle inside that window: an
expired challenge is refused, and reading it again returns the same expired
terms rather than new ones, so a fresh experiment is the only way on.
Retry with the credential
The credential is base64url without padding, wrapping the token and an echo of the challenge:challenge value verbatim from the WWW-Authenticate parameters,
request included as the raw string you received. The API compares your echo
against the challenge it issued, so a re-encoded request is refused even
though it decodes to the same JSON.
Send the credential in the Authorization header under the Payment scheme,
and move your API token to X-Adaptyv-Api-Key:
If the charge succeeds but the response never reaches you, repeat the call. The
API returns the charge it already made rather than making a second one.