# Decide refund requests

> Read the refunds your customers ask for, see what the refund policy says about each one, and approve or reject them.

Source: https://www.coritan.com/docs/organizations/billing/refunds/

In the dashboard:

- /dashboard/organizations/…/billing/refunds: https://www.coritan.com/dashboard/organizations

Your customers ask for a refund from a paid invoice in their account on your storefront. Each request waits on the **Refunds** page of **Billing** until someone decides it, with what the refund policy says about the invoice. To refund an invoice nobody asked about, refund it from the [invoice's page](/docs/organizations/billing/invoices/#refund-an-invoice) instead.

## Before you begin

- You need the owner, admin or billing role.
- Approving and rejecting a request answer the customer, and approving moves money, so Coritan may first ask you to confirm it is you. See [Confirm it is you](/docs/organizations/billing/invoices/#confirm-it-is-you).

## Find a request

1. In the [dashboard](https://www.coritan.com/dashboard/organizations), open the organization, then **Billing**, then **Refunds**. The page opens on the requests still **To decide**, oldest first, with how many there are.
2. To see the decided ones, choose **Approved**, **Rejected**, **Failed**, **Withdrawn** or **All** in place of **To decide**.
3. Type an invoice number, a customer's name, email or company, a service's hostname, or a request, invoice or customer ID in the search box. Each status in the list then counts the requests the search matches in it.
4. Select a request to open it.

The list shows 50 requests a page, oldest first, with the pager under it for the rest, and the search looks through every request, not only the page on screen. While they all fit on one page, select a column heading to sort them. The status, the search, the page and the sort are kept in the address.

## Read a request

A request's page shows:

- **Request**: the **Invoice** and the **Customer**, the **Amount** asked for beside the **Invoice total**, the **Reason** they chose and, when they wrote one, the reason **In their words**, when they **Asked**, and the **Service** the invoice is for with its state.
- **Refund policy**: what the policy says about the invoice as it stood when they asked: the **Refund window**, how long after paying they asked and whether that was inside it, such as `Renewal, 48 hours: asked 11 days after paying, outside the window`, what it was **Paid with**, and whether the money can go **Back to the payment method**. A request made within three days of paying reads in hours, past that in days.
- **Decision**, once it is decided: the **Outcome**, where the money was **Refunded to**, when it was **Decided**, the **Note** the customer read, and **What the gateway said** when the refund failed.

The policy allows a refund of a new subscription within 24 hours of paying, and of a renewal within 48 hours. Notes above the cards say what the policy leaves to you, such as a request made after the window, which you may still meet with wallet credit, or an invoice paid from the wallet, which can only be refunded as wallet credit. A red note says what the policy refuses: an invoice that is not paid or is already refunded, a cryptocurrency payment, or a service ended for breaking the terms of service.

## Approve a request

1. Open the request and select **Approve refund…**.
2. Under **Refund to**, choose **Their payment method**, back to the card or account they paid with, which takes a few days to show, or **Wallet credit**, added to their wallet at once and spent on their next invoices. Only **Wallet credit** is offered when the invoice was not paid through a gateway.
3. Add a **Note to the customer** if you want one. They read it in the email that tells them the decision.
4. Type the amount to confirm, and select **Approve refund**.

The customer is emailed that the refund is on its way, and the message after you approve says how much went back and whether the service ended. Refunding everything still paid on the invoice marks it refunded, and refunding less leaves it paid, less what went back. A refund of the whole invoice in one go also ends the service it is for now; a smaller one leaves the service running. Wallet credit is added in the currency of the customer's wallet. When the gateway declines, the request moves to **Failed**, nothing is refunded and the invoice still reads as paid; open the invoice and refund it from there, to the payment method or as wallet credit.

## Reject a request

1. Open the request and select **Reject…**.
2. Write the **Note to the customer**, at least a sentence, saying why. They read it in the email that tells them the request was rejected.
3. Select **Reject request**.

The money stays with your organization. Rejecting cannot be undone, but the customer can ask again.

## Troubleshooting

**Approve refund…** and **Reject…** are missing
: The request is already decided, or the customer withdrew it. Its **Decision** card says which.

The refund failed
: The gateway refused it, and what it said is under **What the gateway said**. Refund the invoice as **Wallet credit** from its page, or ask the customer to check the card they paid with.

`This request has already been decided`
: Someone decided it while you had it open, or the customer withdrew it. Reload the page.

## Related

- [Organization billing](/docs/organizations/billing/)
- [Manage customer invoices](/docs/organizations/billing/invoices/)
- [See every payment](/docs/organizations/billing/payments/)
- [Handle billing in the staff console](/docs/organizations/staff-console/billing/)

## With the API

List requests, oldest first. `status` takes `pending` (the default), `approved`, `rejected`, `withdrawn`, `failed` or `all`. `q` searches the invoice number, the customer's email, name or company, the service's hostname, and a request, invoice or customer ID. `limit` (50 by default, at most 200) and `offset` page the list, and `with_total=true` adds the counts:

```bash
curl "https://api.coritan.com/api/v1/orgs/acme/staff/refund-requests?status=pending&with_total=true" \
  -H "Authorization: Bearer $CORITAN_TOKEN"
```

The answer has `status`, `pending` (how many wait in all, whatever the status and the search), `can_decide` and `items`. With `with_total=true` it also has `total`, the requests the status and the search match, with `limit`, `offset` and `counts`, which holds `all` and each status for the same search. An unknown `status` answers `422`. Each request has `id`, `status`, `amount`, `currency`, `reason_code`, `reason_text`, `invoice_id`, `invoice_number`, `invoice_total`, `customer_id`, `customer_name`, `customer_email`, `service_id`, `service_hostname`, `service_status`, `eligibility` (what the policy says), `resolution`, `decision_note`, `failure_message`, `decided_at` and `created_at`. Read one with `GET /refund-requests/{request_id}`.

Approve with `resolution` set to `gateway_refund` or `wallet_credit` and an optional `note`; reject with a `note` of at least five characters:

```bash
curl -X POST https://api.coritan.com/api/v1/orgs/acme/staff/refund-requests/12/reject \
  -H "Authorization: Bearer $CORITAN_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{"note": "The server was online for the whole month."}'
```

Approving answers the request as it now stands, with what happened: `refunded` and `currency`, the amount that went back in the invoice's currency; `refunded_usd`, what went back to the payment method in dollars, or `null` for wallet credit; `invoice_status`, which is `paid` while some of the invoice is still paid and `refunded` once nothing is; and `service_ended`, whether the refund ended the service. When the gateway declines, `status` is `failed` and `failure_message` holds what it said.

Both take the owner, admin or billing role, and answer `403` with the code `reauth_required` until the member has confirmed it is them in the last ten minutes. A request that cannot be decided answers `400` with the reason.

## API

- `GET /api/v1/orgs/{org_slug}/staff/refund-requests`: The refund requests, oldest first, so the longest wait is decided first (https://www.coritan.com/docs/api/reference/organizations/org-staff-ops/#op-get-api-v1-orgs-org-slug-staff-refund-requests)
- `GET /api/v1/orgs/{org_slug}/staff/refund-requests/{request_id}`: Staff refund request (https://www.coritan.com/docs/api/reference/organizations/org-staff-ops/#op-get-api-v1-orgs-org-slug-staff-refund-requests-request-id)
- `POST /api/v1/orgs/{org_slug}/staff/refund-requests/{request_id}/approve`: Staff approve refund request (https://www.coritan.com/docs/api/reference/organizations/org-staff-ops/#op-post-api-v1-orgs-org-slug-staff-refund-requests-request-id-approve)
- `POST /api/v1/orgs/{org_slug}/staff/refund-requests/{request_id}/reject`: Staff reject refund request (https://www.coritan.com/docs/api/reference/organizations/org-staff-ops/#op-post-api-v1-orgs-org-slug-staff-refund-requests-request-id-reject)
