> ## Documentation Index
> Fetch the complete documentation index at: https://docs.capcells.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Report a receipt

> Report money that arrived and receive the allocation: where every centavo went, under the rendered rule.

You hold the funds; this call records the arrival and answers where the money went. A Receipt is addressed to a **Client**, never to a Loan — which debt it settles is the allocation's answer — and it is never refused for its size: less than due, more than due, more than the whole Loan and money on a Loan that owes nothing are all recorded. [Payments](/lending/payments) carries the waterfall, the elections and every worked case.

## Path parameters

<ParamField path="tenant_id" type="string" required>
  The Tenancy reporting.
</ParamField>

## Body

<ParamField body="reference" type="string" required>
  Your own name for this arrival, unique within the Tenancy. A retry restating it answers `200` with the allocation on file.
</ParamField>

<ParamField body="client_id" type="string" required>
  The Client who paid. An unregistered one is refused.
</ParamField>

<ParamField body="amount" type="object" required>
  What arrived: `{"minor_units": 90066, "currency": "MXN"}`, in the currency the Loans are in.
</ParamField>

<ParamField body="value_date" type="string" required>
  The day the borrower paid, never defaulted. Allocation, closure and every derived figure key on it — not on when you reported.
</ParamField>

<ParamField body="designated_loan_id" type="string">
  The Loan the borrower named. A designation wins over the default rule, and `chosen_by` says which applied.
</ParamField>

<ParamField body="payoff_intent" type="boolean">
  The borrower's statement that this payment discharges the Loan. A shortfall inside the tolerance closes only against it. Stating it and electing something else states two things about one payment and is refused.
</ParamField>

<ParamField body="election" type="string">
  What money past everything matured does: `principal`, `advance` or `term` — [the borrower's choice](/lending/loans). Absent means the Configuration's own `early_money_treatment` applies.
</ParamField>

<ParamField body="rail" type="string">
  How the money moved: `card`, `spei`, `cash`, `direct_debit`, `other`. Recorded verbatim, read by nothing, part of the Receipt's identity.
</ParamField>

<ParamField body="context" type="object">
  Your key-value object: at most 16 keys, 64 bytes a key, 4096 bytes rendered, string values. Stored, echoed wherever the Receipt or its allocation is read, read by nothing — and part of what a reused `reference` restates.
</ParamField>

<ParamField body="provider_reference" type="string">
  What your provider called the movement, at most 128 bytes. Recorded verbatim, part of the identity — a retry restating a different one is a disagreeing report.
</ParamField>

<ParamField body="quote_id" type="string">
  The [payoff quote you recorded](/api-reference/loans/record-payoff-quote) and relayed, which this money was collected against. Only a Receipt electing the payoff and designating the quote's own Loan may name one. It binds nothing: the Receipt settles against the figure derived today, and the allocation answers whether the money was the recorded figure. Part of the identity.
</ParamField>

## Response

`201` with the allocation — the same answer [reading the Receipt back](/api-reference/receipts/read) returns:

<ResponseField name="receipt" type="object" required>
  The report echoed, with the Platform's `id` and `reported_at` added, and `reversed` false.
</ResponseField>

<ResponseField name="rule" type="object" required>
  The jurisdiction rule the allocation ran under, rendered so the order is read, not inferred: `charge_order`, `period_order`, `undesignated_loans`.
</ResponseField>

<ResponseField name="settled" type="object" required>
  What reached debt, with `residual`, `excess`, `absorbed` and per-Loan rows beside it — [the allocation answer](/lending/payments), field by field.
</ResponseField>

<ResponseField name="loans" type="array" required>
  Each Loan the money reached: `chosen_by`, `settled`, `prepayment`, `owed_back`, `closed_on` where it discharged, the Periods walked with each charge and its tax apart, and `recalculated_plan` where a prepayment recalculated.

  Each Period walked also states where the Receipt left it:

  | Field | What it says |
  | - | - |
  | `settled` | The Period stands settled entire once this Receipt is applied. A Period paid in part reads `false`. |
  | `overdue_from` | The day the Period had become overdue, where it had by the value date. Absent on a Period paid by its tolerance end. |

  Read "was this paid on time?" from `overdue_from`, never by comparing dates yourself.
</ResponseField>

<ResponseField name="quote_id" type="string">
  The payoff quote the Receipt named, echoed. Absent where it named none.
</ResponseField>

<ResponseField name="quoted_figure_agrees" type="boolean">
  Whether the money is exactly the recorded figure, in the same currency. Present exactly where `quote_id` is. `false` refuses nothing and changes nothing settled — it is what a dispute starts from.
</ResponseField>

<ResponseField name="anomalies" type="array" required>
  What the allocation had to resolve or could not do — empty for an ordinary overpayment. Money that reached no Loan is in `excess` and owed to the Client, never dropped.
</ResponseField>

## Refusals

| Condition | Status and code |
| - | - |
| The `reference` names a different report — amount, date, rail, anything | <Badge color="red">409</Badge> `reference_reused` |
| `client_id` is not registered | <Badge color="orange">422</Badge> `unknown_client` |
| Every Loan the Receipt could reach was ceded by its value date | <Badge color="red">409</Badge> `cession_in_force` |
| `payoff_intent` beside an `election` | <Badge color="orange">422</Badge> |
| `quote_id` on a Receipt stating no payoff or designating no Loan, or naming another Loan's quote | <Badge color="orange">422</Badge> `receipt_refused`, naming both Loans |
| `quote_id` names no quote you recorded | <Badge color="orange">404</Badge> `not_found` |
| A missing `value_date`, a malformed amount, an unknown field | <Badge color="orange">400</Badge> / <Badge color="orange">422</Badge> — refused by name |

<RequestExample>
  ```bash Report theme={null}
  BODY='{
    "reference": "receipt-0001",
    "client_id": "c-0001",
    "amount": { "minor_units": 90066, "currency": "MXN" },
    "value_date": "2026-04-06",
    "rail": "spei",
    "provider_reference": "MBAN01002606060099"
  }'

  curl -X POST "https://api.capcells.com/v1/tenants/$TENANT_ID/receipts" \
    -H "Authorization: $(capcells_sign "$CAPCELLS_API_KEY" POST "/v1/tenants/$TENANT_ID/receipts" "$BODY")" \
    -H "Content-Type: application/json" \
    -d "$BODY"
  ```
</RequestExample>

<ResponseExample>
  ```json 201 theme={null}
  {
    "receipt": {
      "id": "93e2afee-c3be-4ac7-a4e4-a9f2645c73ef",
      "reference": "receipt-0001",
      "client_id": "c-0001",
      "amount": { "minor_units": 90066, "currency": "MXN" },
      "value_date": "2026-04-06",
      "payoff_intent": false,
      "rail": "spei",
      "provider_reference": "MBAN01002606060099",
      "reported_at": "2026-08-31T11:29:29.28672Z",
      "reversed": false
    },
    "rule": {
      "jurisdiction": "MX",
      "charge_order": ["penalty", "late_fee", "fee", "interest", "principal"],
      "period_order": "oldest first",
      "undesignated_loans": "most_onerous_then_oldest"
    },
    "settled": { "minor_units": 90066, "currency": "MXN" },
    "residual": { "minor_units": 0, "currency": "MXN" },
    "excess": { "minor_units": 0, "currency": "MXN" },
    "absorbed": { "minor_units": 0, "currency": "MXN" },
    "loans": [
      {
        "loan_id": "23290586-701f-493e-abe2-802c8e5e2b8c",
        "reference": "loan-0001",
        "chosen_by": "default_rule",
        "settled": { "minor_units": 90066, "currency": "MXN" },
        "prepayment": { "minor_units": 0, "currency": "MXN" },
        "residual": { "minor_units": 0, "currency": "MXN" },
        "owed_back": { "minor_units": 0, "currency": "MXN" },
        "periods": [
          {
            "index": 1,
            "due_on": "2026-04-06",
            "total": { "minor_units": 90066, "currency": "MXN" },
            "charges": [
              { "charge": "fee", "amount": { "minor_units": 2083, "currency": "MXN" }, "tax": { "minor_units": 333, "currency": "MXN" }, "total": { "minor_units": 2416, "currency": "MXN" } },
              { "charge": "interest", "amount": { "minor_units": 31344, "currency": "MXN" }, "tax": { "minor_units": 5015, "currency": "MXN" }, "total": { "minor_units": 36359, "currency": "MXN" } },
              { "charge": "principal", "amount": { "minor_units": 51291, "currency": "MXN" }, "tax": { "minor_units": 0, "currency": "MXN" }, "total": { "minor_units": 51291, "currency": "MXN" } }
            ],
            "settled": true
          }
        ]
      }
    ],
    "anomalies": []
  }
  ```
</ResponseExample>


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.