Errors
Last updated: 2026-07-17
Non-2xx responses use a google.rpc.Status-compatible shape:
{
"code": 3,
"message": "currencyCode is required",
"details": []
}
Common code values:
| code | Meaning |
|---|---|
| 3 | INVALID_ARGUMENT (validation) |
| 5 | NOT_FOUND |
| 7 | PERMISSION_DENIED |
| 13 | INTERNAL |
| 16 | UNAUTHENTICATED |
Validation error example (field violations)
{
"code": 3,
"message": "invalid argument",
"details": [
{
"@type": "type.googleapis.com/google.rpc.BadRequest",
"fieldViolations": [
{
"field": "currency_code|payin.currency.required",
"description": "currencyCode is required"
},
{
"field": "amount|payin.amount.required",
"description": "amount must be greater than 0"
}
]
}
]
}
Use fieldViolations to map API validation errors to specific form fields on your side (for example highlight currencyCode input when currency_code|payin.currency.required is returned).
Nested field violations can use snake_case paths. Localized merchant validations may append a |<messageId> suffix, while other validation errors may use just the field path. For example, a missing payout operator can be reported as mobile_money_details.operator, which maps to the JSON field mobileMoneyDetails.operator.
Method temporarily unavailable
When a selected payment method or submethod cannot be used before processing,
the API returns HTTP 400 / INVALID_ARGUMENT with the stable public reason
method_unavailable and this message:
Payment method is temporarily unavailable. Please contact support.
The reason can appear in google.rpc.ErrorInfo.reason and as the suffix of a
field violation. The complete field value includes the operation prefix, for
example CreatePayOutOrder/#payment_method|method_unavailable. A payment
accepted far enough to produce a payment order can instead expose
method_unavailable in paymentOrder.failureReason. Handle this reason
separately from malformed input, offer another discovered method when
appropriate, and do not retry in a tight loop.
Payment failure reasons
When a payment reaches a negative state, paymentOrder.failureReason and the
string-encoded paymentOrder.failureReasonCode can contain these current
values:
failureReason | failureReasonCode | Meaning |
|---|---|---|
internal_error | 1 | Processing error |
unknown | 2 | Unknown reason |
declined | 3 | Declined by the customer or payment partner |
cancelled_by_user | 4 | Customer cancelled the payment |
invalid_request | 5 | Invalid or unsupported payment request |
insufficient_funds | 6 | Insufficient customer or merchant funds, depending on the flow |
expired_payment | 7 | Payment session expired |
expired_payment_form | 8 | Hosted payment form expired |
suspected_fraud | 9 | Payment was rejected as suspected fraud |
provider_unavailable | 10 | Temporary processing unavailability after the payment was created |
amount_out_of_range | 11 | Amount is outside the supported range |
method_unavailable | 12 | Selected method or submethod is temporarily unavailable |
Treat unknown future reason strings and codes as forward-compatible values.
Outcome vs transport status
- Validation/auth/system issues return non-2xx with
rpc.Status. - Payment outcome is carried by
paymentOrder.status(often in HTTP 200 responses). - For mobile-money pay-ins, missing
mobileMoneyDetailsormobileMoneyDetails.mobileNumberis a validation error and returns non-2xx. - For operator-aware mobile-money pay-ins and payouts, a missing required
mobileMoneyDetails.operatoris a validation error and returns non-2xx. - For mobile money transfer, missing
mobileMoneyTransferDetails,.operator, or.mobileNumberis a validation error and returns non-2xx. - For voucher-based mobile-money pay-ins, send
mobileMoneyDetails.voucherPinwhen the selected route requires voucher collection.