Errors

A request that fails returns an HTTP error status and one envelope. Branch on error.code, never on message.

{
  "error": {
    "code": "validation_failed",
    "message": "payer.email is required",
    "details": [{ "field": "payer.email", "message": "is required" }]
  }
}
Field Type Always set Meaning
error.code string yes The cause — see Codes. Stable: branch on it
error.message string yes Human-readable. Not stable — do not parse
error.details[] array for validation_failed One item per field: field — its path, message — what is wrong

Codes

HTTP code When Retry
400 validation_failed A field is missing or malformed; details[] names it. Includes an amount with more than two decimals and a currency other than the shop currency No. Fix the request
401 authentication_failed The key is missing, malformed or revoked, or sent to the other environment's host No
403 method_not_enabled The method is not enabled for the shop, or the key is of the other shop type — a payin shop on a payout endpoint, or the reverse No. Use the key of the right shop, or ask Mercuryo to enable the method
404 resource_not_found No such transaction in this shop No
409 merchant_reference_conflict The merchant_reference is used with a different body No. Resend the original body, or use a new reference
409 action_not_allowed The action is not available for this method or status: capture on a payin that is not authorized, a refund above the remainder No
429 rate_limited Too many requests Yes, after Retry-After seconds
500 internal_error Failure on our side Yes, the identical request
501 not_supported_yet In the contract, not working yet No

Nothing is created on any of them. An unknown code: act on its HTTP status — retry 429 and 500 with the identical request, fix the request on any other.

A decline is a status, not an error

When the bank, the provider or antifraud declines a transaction after it was created, the request still succeeds. The transaction ends failed, and the reason is in status_details.code:

status_details.code Meaning
card_not_supported The card is not accepted: type, country or issuer
invalid_payment_token The Apple Pay or Google Pay token could not be decrypted
method_unavailable The method is not available for this transaction right now
risk_rejected Rejected by antifraud
limit_exceeded A per-transaction, daily or monthly limit
provider_declined The provider or the bank declined
invalid_recipient_details The recipient's bank rejected the payout details
insufficient_funds The shop balance did not cover the payout
canceled_by_payer The payer rejected the payment
canceled_by_merchant You voided the hold
internal_error Failure on our side; the transaction did not complete

Which codes a method can return is listed on its page: Card, Apple Pay, Google Pay, BLIK, Card payout. An unknown code is a decline: handle it like provider_declined.

A decline is final. Repeating the request returns the same failed transaction; a new attempt is a new transaction with a new merchant_reference.

Next: Webhooks