We reproduced an invoice/refund status disagreement in the Square Sandbox with two entirely synthetic test invoices.
- Create an order and invoice, then publish with SHARE_MANUALLY.
- Pay the invoice on Square’s hosted sandbox payment page using the official test card.
- Retrieve the payment ID from the order and call RefundPayment once for the full amount.
- Independently retrieve the invoice, payment and refund after processing.
Both PaymentRefund objects are COMPLETED, and each Payment.refunded_money equals the full original payment. However, both Invoice objects remain PAID at version 2, with unchanged updated_at. All readbacks return HTTP 200. The same result occurs with API versions 2026-08-19 and 2026-09-16, including repeat reads at 15:49, 16:09 and 19:56 UTC on September 16.
The Pay or Refund Invoices guide says a full refund changes the invoice to REFUNDED and updates its version/timestamp. Is there a known sandbox propagation limitation? What supported readback should establish invoice closure before a corrected replacement is created?
We have held replacements and have not attempted another refund or an invoice-status override. No production transaction or customer data is involved. We can provide the exact sandbox resource IDs through a supported private channel if needed.
Reference: Pay or Refund Invoices