PAQ withdrawals
Prefer capability channel execute for PAQ withdrawals. The /channel/paq/* endpoints are the provider-specific alternative and also supply the external-wallet sign/process follow-ups.
Prerequisites#
- API key with PAQ channel enabled
- Profile context for withdraw create
- Valid
codigopaqfor the destination user - Token balance / allowance / gas as required by the chain
Flow overview#
- Validate phone / código
- Preview amounts
- Create withdraw
- If unsigned: fetch sign payload → process sponsored tx
- Poll until
completed,failed, orexpired
1. Validate código#
curl -sS "https://api-stg.vudy.app/channel/paq/validate-phone?codigopaq=USER_CODE" \
-H "x-api-key: vudy_sandbox_YOUR_KEY"const { data } = await fetch(
"https://api-stg.vudy.app/channel/paq/validate-phone?codigopaq=USER_CODE&capabilityId=CAPABILITY_UUID",
{ headers: { "x-api-key": process.env.VUDY_API_KEY } },
).then((r) => r.json());
// { ok, valid, response?, signature? } — signature only when capabilityId is valid and consulta passes
When using capability execute, call POST /channels/paq/validate with paramKey: "codigopaq", then send params.codigopaq as ["USER_CODE", "SIGNATURE"].
2. Preview#
curl -sS "https://api-stg.vudy.app/channel/paq/preview?chain=ethereum&token=0xTOKEN_ADDRESS&amount=50" \
-H "x-api-key: vudy_sandbox_YOUR_KEY"3. Create withdraw#
curl -sS https://api-stg.vudy.app/channel/paq/withdraw \
-H "x-api-key: vudy_sandbox_YOUR_KEY" \
-H "x-profile-id: PROFILE_UUID" \
-H "x-team-id: TEAM_UUID" \
-H "Content-Type: application/json" \
-d '{
"codigopaq": "USER_CODE",
"destinationCountry": "GT",
"chain": "ethereum",
"token": "USDC",
"amount": 50,
"note": "Cash out"
}'const { data } = await fetch("https://api-stg.vudy.app/channel/paq/withdraw", {
method: "POST",
headers: {
"x-api-key": process.env.VUDY_API_KEY,
"x-profile-id": profileId,
"x-team-id": teamId,
"Content-Type": "application/json",
},
body: JSON.stringify({
codigopaq: "USER_CODE",
destinationCountry: "GT",
chain: "ethereum",
token: "USDC",
amount: 50,
// sendWallet, sendAutomatically optional
}),
}).then((r) => r.json());
// External flow: { txId, rechargeId, sendWallet, needsSponsorship, ... }
// Managed session wallet: { signed: true, txId, rechargeId, txHash, ... }
4. Sign and process (when needed)#
Poll GET /channels/paq/{txId}. For an external wallet, a pending transaction without txHash returns actionNeeded: true with sign and process steps:
# Sign payload
curl -sS https://api-stg.vudy.app/channel/paq/withdraw/TX_ID/sign-payload \
-H "x-api-key: vudy_sandbox_YOUR_KEY"
# Process sponsored tx
curl -sS -X POST \
https://api-stg.vudy.app/channel/paq/withdraw/TX_ID/process-sponsored-tx \
-H "x-api-key: vudy_sandbox_YOUR_KEY" \
-H "Content-Type: application/json" \
-d '{"userSignature":"0x..."}'const payload = await fetch(
`https://api-stg.vudy.app/channel/paq/withdraw/${txId}/sign-payload`,
{ headers: { "x-api-key": process.env.VUDY_API_KEY } },
).then((r) => r.json());
// Verify payload.data.signerAddress, then sign payload.data.typedData.
await fetch(
`https://api-stg.vudy.app/channel/paq/withdraw/${txId}/process-sponsored-tx`,
{
method: "POST",
headers: {
"x-api-key": process.env.VUDY_API_KEY,
"Content-Type": "application/json",
},
body: JSON.stringify({ userSignature }),
},
);Status transitions#
| Stage | Status |
|---|---|
| Created | pending |
| Settled | completed |
| Provider/error | failed |
| Timed out | expired |
Capability path#
Use POST /channels/quote + POST /channels/execute with the discovered PAQ capability. If execute returns walletFlow: "internal", providerPayload may include txHash. If it returns walletFlow: "external", poll and perform the returned sign/process steps (or use providerPayload.signPayload / txToExecute).