Payment reconciliation
Reconcile received payments — bank or PSP — with open receivables on the platform. This guide covers allocation proposal and creation of a payment_allocation usable by your financial system.
Business objective
When a buyer pays a receivable, the receipt is represented either by a
psp_payment when observed at a PSP, or by a
payment when received directly, for example through open banking. In both cases, the process must determine which receivables this payment covers.
Reconciliation answers two questions: which receivables does this payment settle?
and which part of the amount remains unallocated? The result is a
payment_allocationthat materializes the allocation fact and advances statuses of relevant documents.
This guide covers buyer-side reconciliation for payment and
psp_paymentsources. An aggregated PSP payout psp_with_allocations is never reconciled with documents: its individual PSP transactions carry the allocations.
Objects involved
| Object | Role in reconciliation |
|---|---|
psp_payment | Buyer receipt observed at a PSP. It may be applied directly to receivables when `succeeded`. |
payment | Buyer receipt received outside a PSP, for example by bank transfer. Aggregated PSP payouts are never applied to documents. |
receivable_allocation | Proposal for distributing an amount over open receivables. Transient object produced by `propose_payment_allocation`. |
payment_allocation | Persisted allocation fact. Links a `payment` or `psp_payment` source to invoices, credit notes, or other selected targets. |
The receivable_allocation is a common object — it is not stored directly but serves as typed input to the reconcile_paymentnode. It carries the list of target receivables and the amounts allocated to each.
Reconciliation journey
A received payment triggers an allocation proposal. Depending on matching, the process creates the application or routes to specific handling.
Payment receipt
A confirmed receipt arrives as psp_payment through a PSP or as
payment through a direct channel. The process may be triggered by the corresponding event or receive the object from a previous step.
Proposer l'allocation
The node propose_payment_allocation searches the company's open invoices within a configurable time window and proposes the best combination. It routes according to the matching result.
Allocate and reconcile
On accepted routes, reconcile_payment receives the
payment or psp_payment and selected proposal, then creates the payment_allocation using the corresponding source type.
Proposer l'allocation
The node propose_payment_allocation is a router. It receives the company, amount, and currency, searches open receivables within the configured window, and returns the best candidate allocation.
Key parameters
| Parameter | Role |
|---|---|
company | Company whose open receivables are searched. |
amount | Received amount, expressed in the currency's minor unit. |
currency | Payment currency. Only receivables in the same currency are considered. |
invoice | Optional. Restricts the search to one precise invoice. |
reference | Optional. Source invoice reference to refine matching. |
invoice_window_past_days | Past search window (default: 180 days). |
invoice_window_future_days | Future search window (default: 30 days). |
Routes and recommended actions
| Route | Meaning | Recommended action |
|---|---|---|
exact_match | The received amount exactly covers a combination of receivables. | Allocate and reconcile directly. |
underpayment | The amount is lower than the total proposed receivables. | Allocate partially; the receivable remains open for the balance. |
overpayment | The amount exceeds the total receivables found. | Decide how to handle the excess — refund, credit note, or pending credit. |
ambiguous | Several combinations of receivables are possible without a discriminating criterion. | Request manual resolution or apply a deterministic business rule. |
unmatched | No open receivable found for the company and amount. | Notify the operations team or create an ad hoc receivable. |
Every route must be wired in the process, even when some lead to an alert or log. An unreconciled payment falling into an unconnected path would otherwise silently stop.
Allocate and reconcile
reconcile_payment
The node receives a retained platform.payment or
platform.psp_payment and the source receivable_allocation. It creates a payment_allocation whose source_type is derived directly from the source object's type.
The receipt channel does not change the business action: in both cases, Ormuz applies a received amount to receivables. Source-specific controls still apply when creating the payment_allocation.
Statuses and outcomes
PSP payment statuses
status | Meaning |
|---|---|
pending | Payment created, funds not yet confirmed. |
partially_funded | Partial amount received (`0 < amount_received < amount`). |
succeeded | Funds confirmed and available for reconciliation. |
A psp_payment must be succeeded before application. For a
payment, the API verifies that it remains in a state allowing allocation and that it is not a payout. psp_with_allocations.
Payment-allocation statuses
status | Meaning |
|---|---|
partial | The source is not fully allocated; part of the amount remains available. |
complete | The source is fully allocated by this application and previous applications. |
A payment_allocation partial are not an error: they simply mean part of the source remains available after this allocation.
Events and tracking
| Event | Use |
|---|---|
psp_payment.succeeded | Trigger a process when a PSP receipt is confirmed. |
payment.received | Trigger a process when a non-PSP receipt is recorded. |
payment_allocation.complete | Source allocation is complete; export the result to the financial system when needed. |
payment_allocation.partial | Part of the source remains unallocated and may require additional handling. |
invoice.paid | An invoice is fully settled after allocation. |
invoice.partially_paid | An invoice is partially settled; the balance remains due. |
Events payment_allocation.complete and
payment_allocation.partial expose the allocation result. Events on relevant documents simultaneously let you track their evolution.
Integration checklist
Configure the trigger appropriate to the channel:
psp_payment.succeededfor a PSP orpayment.receivedfor a direct receipt.Make sure the company associated with the source has open receivables before proposing an allocation.
Wire every route of
propose_payment_allocation—exact_match,underpayment,overpayment,ambiguous,unmatched.Explicitly handle routes
ambiguousandunmatched— operational alert, deterministic rule, or manual resolution.Pass the retained
paymentorpsp_paymentand theallocation_proposalsource to thereconcile_payment.Consommer
payment_allocation.completeandpayment_allocation.partialnode idempotently.On a
partialpartial application, explicitly decide how to handle the source amount still available.Reread the
payment_allocationfrom the API before any accounting update when your integration needs the complete line details.