Quick Start
This guide walks you through creating a crypto payment, launching the hosted payment page, and confirming the final outcome. It also includes the required behavior for underpayments and overpayments.
What you will build
Create a hosted crypto payment session
Present the hosted payment page to a customer
Confirm payment completion using webhooks or status polling
Handle
underpaidandoverpaidoutcomes correctlyUnderstand the reclaim flow for any unconverted crypto
Prerequisites
You will need:
A sandbox terminal API key, which is the secret
apiKey, not a masked valueA sandbox
merchantIdandterminalIdA server or tool capable of making HTTPS requests, such as curl, Postman, or your backend
A compatible crypto wallet funded with the real asset and real network fee token required for the tender you are testing
Optional but recommended:
A webhook endpoint for payment status updates
Bead Sandbox crypto payments use live blockchain networks. Test payments require real assets and real network fee tokens. Keep test amounts small.
For USDC on Base and USDC on Solana, the minimum Bead payment amount is $1.00 USD. This minimum is separate from any live-network fee the payer's wallet may require to submit the transaction, such as ETH on Base or SOL on Solana.
Environment and base URLs
Common sandbox base URL:
https://api.test.devs.beadpay.io
Payments endpoints used in this quick start:
POST /Payments/cryptoGET /Payments/{id}/tracking
Authentication used in this quick start:
X-Api-Key: {apiKey}
Sandbox crypto payments use live blockchain networks. Sandbox changes the Bead API environment, merchant configuration, credentials, and hosted payment environment. It does not mean crypto payments are sent over blockchain testnets.
Step 1: Create a payment
Create a hosted payment session and receive a paymentId plus one or more hosted paymentUrls.
For USDC on Base and USDC on Solana, create payments with requestedAmount of 1.00 or higher.
Request
Headers:
Minimal body:
For USDC on Base and USDC on Solana, the smallest valid Bead payment request is:
Recommended additions:
refundEmail: If you have an email address for the payer, include it. This is the email Bead uses to send reclaim instructions when reclaim is required.redirectUrl: If you want the hosted experience to return the shopper to your confirmation page.webhookUrls: If you want webhooks for this payment in addition to any terminal level webhook configuration.
Example expanded body:
Example curl
Example USDC test payment curl:
Response
You will receive a response similar to:
Save:
paymentId: your primary lookup key for status checks, webhooks, reporting, and supportpaymentUrls[0]: the hosted payment page URL to present to the customer
Step 2: Present the hosted payment page
Open the hosted page URL from paymentUrls.
Common options:
Web: open in a new tab or window, or embed if allowed in your flow
Mobile: open in an in-app browser or webview
POS or terminal assisted: display the hosted page on a customer facing device
What the customer will do in a typical crypto wallet flow:
Select an asset, such as BTC or USDC
View a QR code or payment details
Open their wallet app and scan the QR code
Manually enter the crypto amount in their wallet app
Submit the transfer
Important: because the wallet requires the payer to enter an amount manually, miskeyed amounts can result in underpaid or overpaid.
The payer's wallet must hold the correct asset on the correct live network. For example, USDC on Base requires USDC on Base for the payment amount and ETH on Base for network fees. USDC on Solana requires USDC on Solana for the payment amount and SOL for network fees.
Step 3: Confirm the final result
You should always confirm the final status before fulfilling an order. Use either webhooks or status polling.
Option A: Webhooks, recommended
If you configured webhooks, either terminal level or per payment webhookUrls, your server will receive events when the payment status changes.
Recommended handling:
Verify the webhook signature if your configuration supports it
Persist the event quickly
Return
200 OKpromptlyTreat the webhook as the primary status signal
Option B: Polling
Use the tracking endpoint with the paymentId until the payment reaches a terminal status.
Request:
Example curl:
Recommended polling behavior:
Use a reasonable interval, such as 2 seconds, during an active checkout
Stop polling once a terminal status is returned
Prefer webhooks for production scale
Step 4: Handle status outcomes
The payment status is returned in statusCode.
Non terminal statuses
created
Payment created, waiting for customer action
processing
Funds detected and processing is in progress
Terminal statuses
completed
Customer paid the requested amount
Fulfill and mark as paid
underpaid
Customer sent less than requested
Treat as not successful payment, do not fulfill
overpaid
Customer sent more than requested
Treat as not successful payment, do not fulfill
expired
Payment window ended without a valid completion
Treat as not successful payment, do not fulfill
invalid
Irregular condition, funds not eligible for conversion
Treat as not successful payment, do not fulfill
cancelled
Payment cancelled
Treat as not successful payment, do not fulfill
Underpayments and overpayments
Underpayments and overpayments occur because the payer manually enters the crypto amount in their wallet app.
Underpaid
Definition: the payer sent less than the requested amount.
Integrator behavior:
Treat as not successful payment
Do not fulfill the order
If the customer still wants to pay, create a new payment and start a new hosted checkout session
What Bead does:
The crypto received remains unconverted
The full amount received is returned to the payer through the reclaim process
Overpaid
Definition: the payer sent more than the requested amount.
Integrator behavior:
Treat as not successful payment
Do not fulfill the order
If the customer still wants to pay, create a new payment and start a new hosted checkout session
What Bead does:
The crypto received remains unconverted
The full amount received is returned to the payer through the reclaim process
Reclaiming unconverted crypto
Reclaim is how Bead returns any unconverted crypto to the payer.
Reclaim can occur when the payment is:
underpaidoverpaidexpiredinvalidcancelled
Email behavior for reclaim
If you provided
refundEmailin the Create Payment request, Bead emails reclaim instructions to that address when reclaim is required.If
refundEmailwas not provided, the hosted payment page prompts the payer to enter an email address in underpaid and overpaid outcomes so Bead can send reclaim instructions.
Recommended best practice:
Provide
refundEmailwhenever you have it, especially for digital and virtual checkout flows.
Troubleshooting
401 Unauthorized
Common causes:
Missing
X-Api-KeyheaderUsing a masked value instead of the real
apiKeyUsing a key from the wrong environment
Hosted payment page does not load
Common causes:
Using an old or incorrect
paymentUrlsvalueTerminal is not configured for the tender types you are testing
Environment mismatch between API base URL and hosted page environment
Payment creation returns a validation error
Common causes:
For USDC on Base or USDC on Solana,
requestedAmountis less than1.00The tender type in
tenderTypesis not enabled for the merchant, location, or terminalRequired fields for the configured terminal or tender flow are missing
Wallet cannot send the payment
Common causes:
The wallet has the payment asset but not the required live-network fee token
The wallet asset is on the wrong network, such as USDC on Solana instead of USDC on Base
The wallet cannot scan the QR code or send to the address or invoice shown on the hosted payment page
Status never reaches a terminal state
Common causes:
Customer did not complete the wallet transfer
Customer sent funds on the wrong network
Customer sent funds to an old or recently used address instead of the current hosted payment page address
Webhook endpoint is failing and you are relying only on webhooks without polling
Payment reached expired before the customer paid
The quote window timed out. The expired payment URL cannot be reused. Direct the customer to a new payment session. If they sent funds after the session expired, Bead's reclaim process will return them.
Next steps
After you complete this quick start in sandbox:
Review Payment Statuses for full status definitions and guidance
Review Under and Over Payment Handling for detailed integrator workflows
Review Reclaiming Unconverted Crypto to understand reclaim timing and payer experience
Review Test Crypto Transactions for live-network testing instructions and wallet funding guidance
Implement production grade webhooks and internal state mapping before going live
Last updated