Skip to main content

Payment callbacks

Use payment callbacks for request-level transaction state updates after a Checkout payment request has been created.

This page documents the callback payload family separately from:

  • GET /payments/status, which is your polling endpoint
  • notify events, which are lighter lifecycle messages

What a callback represents​

A payment callback is a request-level transaction snapshot.

Treat it as a durable state update for the whole payment request, not just one payer attempt.

Current frozen Sandbox evidence covers these request-level callback states:

  • Completed
  • Cancelled

Additional terminal variants may be added later, but these two shapes are already frozen in the retained contract fixtures used by the docs test suite.

Contract summary​

Every callback snapshot currently includes:

  • id
  • transaction_id
  • amount
  • payments_status
  • fees
  • currency
  • status
  • timestamps
  • payers
  • payees
  • fraud_check_status

Completed callback example​

{
"id": "opaque-payment-id-a8Q3x",
"transaction_id": "merchant-order-a8Q3x",
"amount": "25.00",
"payments_status": {
"paid": "25.00 TTD",
"remaining": "0.00 TTD",
"metadata": []
},
"fees": {
"total": "3.91",
"card_processing": "3.91",
"platform_processing": "0.00",
"agent_processing": "0.00",
"payer_pays": "0.00",
"payee_pays": "0.00",
"merchant_pays": "3.91",
"convenience": "0.00"
},
"currency": "TTD",
"status": "Completed",
"timestamps": {
"created_time": "2026-08-10 08:15:09",
"updated_time": "2026-08-11 02:42:21",
"expire_time": "2026-08-10 11:15:09"
},
"payers": [
{
"mobile_number": "+1XXXXXXXXXX",
"amount": "25.00",
"payment_channel": "payment_link",
"payment_method": "card",
"fee": "0.00",
"tip": "0.00",
"tax": "0.00",
"convenience_fee": "0.00",
"status": "Completed",
"expire_time": "2026-08-10 11:15:09",
"metadata": "",
"url": "https://sandbox.paywise.co/example-hosted-payment",
"expire_date_time": "2026-08-10 11:15:09"
}
],
"payees": [
{
"mobile_number": "+1XXXXXXXXXX",
"amount": "21.09",
"delay_days": 0,
"fees_covered": 0,
"fee": "3.91"
}
],
"fraud_check_status": "passed"
}

Cancelled callback example​

{
"id": "opaque-payment-id-cancel-wallet",
"transaction_id": "journey-wallet-cancel-20260814a",
"amount": "25.00",
"payments_status": {
"paid": "0.00 TTD",
"remaining": "25.00 TTD",
"metadata": []
},
"fees": {
"total": "0.50",
"card_processing": "0.00",
"platform_processing": "0.50",
"agent_processing": "0.00",
"payer_pays": "0.00",
"payee_pays": "0.00",
"merchant_pays": "0.50",
"convenience": "0.00"
},
"currency": "TTD",
"status": "Cancelled",
"timestamps": {
"created_time": "2026-08-14 13:18:00",
"updated_time": "2026-08-14 13:19:08",
"expire_time": "2026-08-14 16:18:00"
},
"payers": [
{
"mobile_number": "+1XXXXXXXXXX",
"amount": "25.00",
"payment_channel": "payment_link",
"payment_method": "wallet",
"fee": "0.00",
"tip": "0.00",
"tax": "0.00",
"convenience_fee": "0.00",
"status": "Cancelled",
"expire_time": "2026-08-14 16:18:00",
"metadata": "",
"url": "https://paywise.app.link/example-wallet-payment",
"expire_date_time": "2026-08-14 16:18:00"
}
],
"payees": [
{
"mobile_number": "+1XXXXXXXXXX",
"amount": "24.50",
"delay_days": 0,
"fees_covered": 0,
"fee": "0.50"
}
],
"fraud_check_status": "passed"
}

How to use callbacks safely​

  • Treat delivery as at-least-once
  • Make your receiver idempotent
  • Do not assume event order from network arrival time alone
  • Persist transaction_id, id, status, and your receive timestamp
  • Use GET /payments/status when you need the latest normalized state

Callback vs status lookup​

  • Callback: push-style request snapshot
  • Status lookup: pull-style current state by payment_details_id

If callback delivery and polling disagree temporarily, prefer the latest successful GET /payments/status result as the operational source of truth.