Skip to main content

Refund a transaction

Return funds to a customer for a captured transaction. You can refund the full amount or part of it. For information on underlying ledger concepts and balance limitations, see Refunds.

Flow overview

Prerequisites

  • The transactionId of a captured transaction (a sale, or a captured authorize). This is the id returned when the transaction was created.

Set your environment variables first:

export API_URL="staging-api"
export API_KEY="Your API Key Here"
export ORGANIZATION_ID="Your Organization ID Here"

Full refund

Omit the amount field to refund the entire refundableAmount. You can send an empty body.

curl -X POST \
"https://${API_URL}.payments.ai/v1/public-api/organizations/${ORGANIZATION_ID}/transactions/{transactionId}/refund" \
--header "Content-Type: application/json" \
--header "Authorization: ApiKey ${API_KEY}" \
--data-raw '{}'

On success, the transaction status updates to refunded.

Partial refund

Set amount to refund part of the captured total. For example, to refund $1.00 of a $2.00 charge:

curl -X POST \
"https://${API_URL}.payments.ai/v1/public-api/organizations/${ORGANIZATION_ID}/transactions/{transactionId}/refund" \
--header "Content-Type: application/json" \
--header "Authorization: ApiKey ${API_KEY}" \
--data-raw '{
"amount": 1
}'

The amount must be greater than zero and no larger than the transaction's refundableAmount. On success, the status updates to partially-refunded and refundableAmount decreases by the refunded amount. You can issue further partial refunds until the full amount is returned.

Response

The endpoint returns a new Transaction object linked directly to the original transaction record. Perform a GET request on the original transaction to confirm its updated state:

curl -X GET \
"https://${API_URL}.payments.ai/v1/public-api/organizations/${ORGANIZATION_ID}/transactions/{transactionId}" \
--header "Content-Type: application/json" \
--header "Authorization: ApiKey ${API_KEY}"

Errors

CodeWhenWhat to do
409 ConflictThe transaction's state does not allow a refund because it is already fully refunded, not refundable, or a refund action is currently in progress. The response body contains no details field.Treat as "cannot refund in the current state". Perform a GET request on the transaction to read its status and refundableAmount.
422 Unprocessable ContentThe requested amount exceeds refundableAmount, equals zero or less, or utilizes an invalid decimal precision. The response body includes a details field.Parse the details field, correct the amount value, and retry the request.

See Errors for the full reference.

Webhooks

A successful refund triggers the transaction-processed notification, which passes the refund's type: "refund" inside the payload. A declined refund triggers a transaction-declined event. There is no dedicated transaction-refunded event. Filter for type === "refund" inside your transaction-processed webhook handler. See Refunds — Webhooks.