Issue an explicit refund against an RMA
Authorization: requires returns:write + payments:write API-key scopes
AND the per-user payments.refund_void permission (SoD parity sweep
2026-05-16; refunds are highest-trust AICPA SoD action). System-actor
calls denied.
Phase A canonical: refundReturn() extracted from postReturnFinancialSettlement. Routes by payment_method:
- original/check/cash: calls processRefund (Stripe + GL via postRefundEntry)
- store_credit: calls issueCreditMemo (DR sales_returns_allowances / CR customer_credits)
Multi-source refund (allocations[]): when the invoice was paid via 2+
payment sources, pass allocations: [{ payment_id, amount, reason? }, ...]
to split the refund across those sources (operator-picks, industry
standard per Stripe + NetSuite — no auto-routing). Each payment_id must
be an order_payments.id on the RMA’s original order and
SUM(allocations[].amount) must equal the total refund (within 1 cent).
Every allocation refunds inside ONE transaction under one GL batch_id;
a failure on any allocation rolls back the whole refund. Card-source
allocations do NOT refund the original processing fee (non-recoverable).
State guard: must be received, inspecting, restocked, written_off, sent_to_vendor, or closed. Idempotency: same amount on same RMA returns cached result; different amount returns 409. Rule 23 SSOT: returns.refund_amount written only by this endpoint. Compound scope required: returns:write AND payments:write.
Authorizations
API key issued per entity via Settings > Developers > API Keys.
Each key carries scopes (e.g. orders:read, products:write).
Bearer token format: Authorization: Bearer ark_live_ent_Test keys use ark_test_ent_. Both are issued per entity
via Settings > Developers > API Keys.
Headers
Client-generated unique key for idempotent POST/PATCH/DELETE operations. Alias for the Idempotency parameter. Max 255 chars. On retry with the same key, the original response is returned without re-executing the operation. Keys expire after 24 hours.
255Path Parameters
Body
Refund amount. Defaults to sum of return_items.refund_amount. When allocations[] is supplied, must equal SUM(allocations[].amount).
Single-source path only. Ignored when allocations[] is supplied.
original, store_credit, check, cash Multi-source refund split. When present, the refund is executed per-payment across these order_payments rows (operator-picks). SUM(allocations[].amount) must equal the total refund within 1 cent.
Response
Refund issued

