status field of every order and they drive webhook events.
States
A final state is terminal —
status will not change again. To reverse a SUCCESS, you create a new order in the opposite direction (or a refund flow, where supported).
Inbound (IN) state machine
Inbound orders start inPENDING immediately. There is no approval step — the platform submits to the provider as part of POST.
Outbound (OUT) state machine
Outbound orders pause inAWAITING_APPROVAL until you explicitly approve. This gate is where you implement business rules — dual control, anti-fraud, balance verification.
What you can do per state
approve and cancel are valid only in AWAITING_APPROVAL. Any attempt at another state returns PAYMENT_ORDER_NOT_AWAITING_APPROVAL or PAYMENT_ORDER_INVALID_STATE (HTTP 422).
Webhook events per transition
Every state transition fires a webhook event:
See Payment events for full event payloads.
Polling vs. webhooks
- Webhooks are the recommended source of truth — they push immediately on transition.
- Polling (
GET .../paymentOrders/{id}) is a valid fallback when you cannot expose a webhook endpoint, but be mindful of rate limits.
Error fields on FAILED
When status is FAILED, the order exposes:
Common
errorCode values include INSUFFICIENT_FUNDS, RECIPIENT_INVALID, LIMIT_EXCEEDED. Branch on errorCode, not errorMessage.
EXPIRED is final, even if the payer pays late
For inbound dynamic QR codes, EXPIRED is terminal. If the payer pays after expiration:
- The PIX network typically rejects the payment at their end (the QR is no longer valid).
- In rare cases where settlement is force-completed, the funds may still appear in your wallet. They will not transition the order — they remain as an unattributed balance entry visible in the wallet ledger.
SUCCESS. Reconcile against your local ledger.
State invariants
A few rules to internalize:- A payment order cannot move from a final state to a transitional state.
directionis set at creation and never changes.idempotencyKeyis set at creation and never changes.amountandnetworkare set at creation and never change.errorCodeanderrorMessageare populated only onFAILED;nullotherwise.processedAtisnulluntil the order leavesPENDINGfor the first time; once set, it does not change.
Next
Payments overview
The payment-order resource model.
Pix cash-in tutorial
End-to-end inbound flow.
Webhooks
Receive state transitions in real time.