Create a withdrawal
title: "Create a withdrawal" description: "POST /v1/withdrawals — sweep a pocket balance to an external wallet." section: "API reference" order: 31 updated: "2026-04-18" sourcePath: "content/docs/api/withdrawals/create.mdx"
POST/v1/withdrawals
Withdraws funds from a pocket to an external address. BchainPay signs the transaction in our vault, broadcasts it on-chain, and fires a withdrawal.completed webhook with the resulting tx_hash.
Request body
| Field | Type | Required | Description |
|---|---|---|---|
| pocket_id | string | required | Source pocket ID, e.g. pkt_usdc_polygon. |
| amount_cents | integer | required | Amount to withdraw in minor units of the pocket coin. |
| destination | string | required | On-chain address on the same network as the pocket. |
| fee_strategy | string | optional | standard (default) or fast. Affects the gas tip we use. |
| reference | string | optional | Your internal reference; echoed in the withdrawal webhook. |
Example
curl -X POST https://api.bchainpay.com/v1/withdrawals \
-H "Authorization: Bearer $BCHAINPAY_API_KEY" \
-H "Idempotency-Key: $(uuidgen)" \
-H "Content-Type: application/json" \
-d '{
"pocket_id": "pkt_usdc_polygon",
"amount_cents": 4999,
"destination": "0xC0ffeeB45...",
"fee_strategy": "standard",
"reference": "PAYOUT-2026-04-18-001"
}'Response — 202 Accepted
{
"id": "wd_8H2x...91",
"object": "withdrawal",
"status": "broadcasting",
"pocket_id": "pkt_usdc_polygon",
"amount_cents": 4999,
"destination": "0xC0ffeeB45...",
"network_fee_cents": 12,
"tx_hash": null,
"reference": "PAYOUT-2026-04-18-001",
"created_at": "2026-04-18T12:05:33Z"
}The withdrawal moves through queued → broadcasting → completed. A tx_hash appears once broadcast. The withdrawal.completed webhook fires after the network confirms.
Errors
| Status | Code | Meaning |
|---|---|---|
400 | insufficient_balance | Pocket balance is below amount_cents + network_fee_cents. |
400 | address_network_mismatch | Destination address is not valid on the pocket's network. |
400 | address_blocked | Destination matches a sanctioned address list. |
409 | pocket_locked | Another withdrawal is already in flight for this pocket. |