UCP Payment Handlers
Before writing code
Fetch live docs:
Conceptual Architecture
Trust Triangle
Business <——> PSP <——> Credential Provider
- Credential Provider (Google Pay, Shop Pay): Issues encrypted payment tokens to the Platform
- PSP (Stripe, Adyen, etc.): Decrypts tokens, authorizes with card networks, settles funds
- Business: Configures which handlers/PSPs it accepts; receives credentials from Platform, forwards to PSP
Critical security rule: Credentials flow Platform → Business ONLY. Business MUST NEVER echo credentials back to the Platform.
Payment Handler Concept
A payment handler is a specification, not an entity. It defines:
id: Unique identifier for this payment handler instance
name: Reverse-domain identifier (e.g., com.google.pay, com.shopify.shop_pay)
version: Date-based version
spec: URI to the handler specification
config: Handler-specific configuration (merchant ID, accepted card networks, tokenization params)
config_schema: JSON Schema defining the structure of the config object for this handler
instrument_schemas: Schemas defining the shape of payment instruments this handler produces
Handlers are declared in the Business's discovery profile and echoed in checkout responses.
Three Payment Processing Scenarios
- Digital Wallet (Google Pay, Shop Pay): Platform acquires encrypted tokens from the wallet provider's API, sends to Business in
complete_checkout.
- Direct Tokenization: Platform calls PSP endpoint directly with Business's public key, gets network tokens.
- Autonomous Agent (AP2): Agent generates cryptographically-signed mandates proving user authorization — no human interaction needed. See the
ucp-ap2-mandates skill.
Credential Flow in Complete Checkout
When calling complete:
payment_data.instrument: Describes the payment method (type, brand, last digits, billing address)
payment_data.credential: The actual token/cryptogram (encrypted, handler-specific)
Implementation Guidance
Business side:
- Configure your PSP (Stripe, Adyen, etc.) and get merchant credentials
- Build payment handler config for your discovery profile — fetch the exact format from the live handler spec
- On
complete_checkout, extract the credential and forward it to your PSP for authorization
- Map PSP responses back to UCP checkout status (completed, or error with messages)
Platform side:
- Read
payment.handlers from the checkout response
- Use the handler's
config to initialize the payment provider SDK (e.g., Google Pay JS API)
- Acquire a payment credential from the user
- Send it in the
complete_checkout call
Always verify the exact handler config schema from the live spec — payment handler configurations change frequently.
1---2name: ucp-payment-handlers3description: Implement UCP payment handlers — configure Google Pay, Shop Pay, or custom payment methods with tokenization, credential flow, and instrument schemas. Use when integrating payment processing into a UCP checkout.4---56# UCP Payment Handlers78## Before writing code910**Fetch live docs**:11- Google Pay handler: https://developers.google.com/merchant/ucp/guides/google-pay-payment-handler12- Shop Pay handler: Web-search `site:shopify.dev UCP Shop Pay payment handler`13- Payment architecture: https://ucp.dev/specification/overview/ (payment section)14- Reference types: https://ucp.dev/specification/reference/ (credential and instrument schemas)1516## Conceptual Architecture1718### Trust Triangle1920```21Business <——> PSP <——> Credential Provider22```2324- **Credential Provider** (Google Pay, Shop Pay): Issues encrypted payment tokens to the Platform25- **PSP** (Stripe, Adyen, etc.): Decrypts tokens, authorizes with card networks, settles funds26- **Business**: Configures which handlers/PSPs it accepts; receives credentials from Platform, forwards to PSP2728**Critical security rule**: Credentials flow Platform → Business ONLY. Business MUST NEVER echo credentials back to the Platform.2930### Payment Handler Concept3132A payment handler is a **specification**, not an entity. It defines:33- `id`: Unique identifier for this payment handler instance34- `name`: Reverse-domain identifier (e.g., `com.google.pay`, `com.shopify.shop_pay`)35- `version`: Date-based version36- `spec`: URI to the handler specification37- `config`: Handler-specific configuration (merchant ID, accepted card networks, tokenization params)38- `config_schema`: JSON Schema defining the structure of the `config` object for this handler39- `instrument_schemas`: Schemas defining the shape of payment instruments this handler produces4041Handlers are declared in the Business's discovery profile and echoed in checkout responses.4243### Three Payment Processing Scenarios44451. **Digital Wallet** (Google Pay, Shop Pay): Platform acquires encrypted tokens from the wallet provider's API, sends to Business in `complete_checkout`.462. **Direct Tokenization**: Platform calls PSP endpoint directly with Business's public key, gets network tokens.473. **Autonomous Agent (AP2)**: Agent generates cryptographically-signed mandates proving user authorization — no human interaction needed. See the `ucp-ap2-mandates` skill.4849### Credential Flow in Complete Checkout5051When calling complete:52- `payment_data.instrument`: Describes the payment method (type, brand, last digits, billing address)53- `payment_data.credential`: The actual token/cryptogram (encrypted, handler-specific)5455### Implementation Guidance5657**Business side:**581. Configure your PSP (Stripe, Adyen, etc.) and get merchant credentials592. Build payment handler config for your discovery profile — fetch the exact format from the live handler spec603. On `complete_checkout`, extract the credential and forward it to your PSP for authorization614. Map PSP responses back to UCP checkout status (completed, or error with messages)6263**Platform side:**641. Read `payment.handlers` from the checkout response652. Use the handler's `config` to initialize the payment provider SDK (e.g., Google Pay JS API)663. Acquire a payment credential from the user674. Send it in the `complete_checkout` call6869Always verify the exact handler config schema from the live spec — payment handler configurations change frequently.