Settlement Reporting

Reconcile settled funds to source transactions with per-SubMID settlement reports, delivered via API or SFTP

CrissCross produces a structured settlement report at the time of each settlement, delivered alongside the wire. Every report ties one bank credit you receive back to the individual transactions — collections, refunds, payouts, fees, FX, and adjustments — that produced it, so you can reconcile against your own ledger.

The reporting model is built on one guarantee:

One file = one SubMID = one settlement = one wire.

Each settlement produces exactly one report, sharing a single SettlementID with the wire it accompanies. There is no wire without a file, and no file without a wire.

Settlement reports are available through two delivery channels — API and SFTP — and you choose which one per SubMID. See Delivery channels.

MID and SubMID

Settlement is organised around a two-level merchant hierarchy. Understanding it is the key to reading a settlement report, because every report is scoped to a single SubMID.

TermMeaningExample
MID (Merchant ID)The parent merchant account — your company as a whole. Groups one or more SubMIDs and is how CrissCross identifies you as a legal entity.Acme
SubMID (Sub-Merchant ID)A child account under a MID, scoped to a single market / processing currency. Each SubMID settles independently, on its own cadence, and produces its own files and wires.AcmeKES, AcmeNGN

A single MID typically has several SubMIDs — one per currency it collects in:

Merchant hierarchy
Acme ← MID (parent merchant)
├── AcmeKES (KES → USD) ← SubMID, settles in USD
├── AcmeNGN (NGN → USD) ← SubMID, settles in USD
└── AcmeZAR (ZAR → USD) ← SubMID, settles in USD

Because a SubMID is scoped to one processing currency, settlement always happens per SubMID: AcmeKES and AcmeNGN settle separately, each on its own schedule, each producing a distinct file and wire.

Each SubMID carries an account code (for example M1002345) that appears in the file name and in the file’s Merchant Account field. See How MID and SubMID appear in the file.

How settlement works

The settlement engine runs on each SubMID’s configured cadence (its settlement delay, e.g. T+2, is a per-SubMID property). For each cycle:

1

Batch transactions

Collect every transaction for the SubMID since the last settlement event that is in scope for this cycle.

2

Compute net

Apply the rolling net model (below) to derive the settlement amount in the processing currency.

3

Apply the FX rate

Convert each transaction into the settlement currency (typically USD) at its all-in rate — the mid-market rate plus the agreed spread. When a transaction was priced by a rate lock it settles at that locked rate, so lines in one file can carry different rates; each line records its AllInRate, RateLockId, and when the lock was struck (RateLockCreatedAt). The header AllInRate is the amount-weighted average of these per-line rates across the settlement.

4

Send the wire

The wire is sent with the payment reference MID:{merchant_id}|STL:{settlement_id}, so you can match the credit on your bank statement to the report.

5

Generate the report

The file is produced atomically with the wire, sharing the same SettlementID, and delivered via the SubMID’s configured channel.

Settlements are only produced when there is activity. A cycle with no in-scope transactions generates no file and no wire.

The settlement model

The net settlement amount is a rolling net, computed per SubMID per cycle:

NetSettlementAmount =
(collections + refund_returned + payout_reversed + positive_adjustments + reserve_releases)
− (refunds + payouts + negative_adjustments + reserve_holds)
− processing_fees

Fees are netted internally on both inflows and outflows:

  • Collections — the customer pays Gross. Net = Gross − Fee, and you receive Net.
  • Refunds / payouts — the customer or beneficiary receives the full requested amount; the fee is an additional deduction from your balance. Gross is shown negative, Fee positive, and Net = Gross − Fee.

Each line carries its gross in the processing currency and its net already converted to the settlement currency at that transaction’s all-in rate — so the sum of the line Net values equals the header Net Settlement Amount, and the wire, with no further conversion. In the totals, Gross Total is in the processing currency while Fees Total and Net Settlement Amount are in the settlement currency; each total names its own currency.

The settlement report file

  • Format: CSV, UTF-8, RFC 4180.
  • Structure: self-describing. Every row starts with a RecordType column — a settlement-level HEADER row followed by N transaction LINE rows. Each section is preceded by its own field-name row, so the file can be parsed without an external schema.
  • Naming: {SubMID}_{SettlementDate:YYYYMMDD}_{ProcessingCurrency}_{SettlementID}.csv
Example file name
M1002345_20260416_NGN_STL000123456.csv

Reading the name: SubMID account M1002345, settled on 2026-04-16, processing currency NGN, settlement STL000123456.

Header fields

Every header field describes the settlement as a whole. Monetary totals are in the settlement currency.

FieldDescription
RecordTypeHEADER for this row.
SettlementIDUnique identifier — 1:1 with this file and the wire.
Company AccountThe MID — the parent merchant (HQ).
Merchant AccountThe SubMID account code — constant across the file, scoped to one processing currency.
Merchant NameDisplay name of the SubMID entity.
Settlement DateWhen the funds are settled (ISO 8601, UTC).
Processing Currency / Settlement Currencye.g. NGN / USD.
AllInRateThe amount-weighted average of the per-line AllInRate values across the settlement — processing units per 1 settlement unit (e.g. 1577.02, i.e. ~1 USD = 1577 NGN), inclusive of spread. Because lines can each settle at their own locked rate, this is a blend; the per-line AllInRate is authoritative for each transaction, so reconcile from the line Net values rather than by applying this rate to the gross total.
RateSourceSource of the mid-market rate the all-in rate was built from, e.g. Bloomberg.
Gross Total / Gross Total CurrencySum of line gross, in the processing currency.
Fees Total / Fees Total CurrencySum of processing fees, in the settlement currency.
Net Settlement Amount / Net Settlement Amount CurrencyThe wired amount, in the settlement currency.
Transaction CountTotal number of LINE rows in the file.

How MID and SubMID appear in the file

The two-level hierarchy maps onto the file’s columns as follows:

ConceptFile fieldExample value
MID (parent merchant)Company AccountAcme
SubMID (account code)Merchant AccountM1002345
SubMID (display name)Merchant NameAcmeNGN

Line fields

Each line represents one transaction. Monetary amounts are in the processing currency and are signed (+ inflow, outflow).

FieldDescription
RecordTypeLINE for a transaction row.
Company Account, Merchant AccountEcho of the header.
SessionIDSession identifier for the customer journey.
PSP ReferenceCrissCross transaction ID.
Merchant ReferenceYour own reference, if supplied on the transaction.
Original PSP ReferencePopulated for REFUND, REFUND_RETURNED, PAYOUT_REVERSED, CHARGEBACK.
Payment MethodCARD / BANK_TRANSFER / MOBILE_MONEY / WALLET / ADJUSTMENT / RESERVE.
Creation Date / Booking DateISO 8601 timestamps (UTC).
Gross / Gross CurrencyAmount in the processing currency (signed: + inflow, outflow).
Initiation Amount / Initiation CurrencyGross converted to the merchant’s initiation currency at this line’s AllInRate.
Processing Fee / Fee CurrencyFee in the settlement currency (always a positive deduction).
AllInRateThe all-in rate applied to this line (processing → settlement, inclusive of spread). Reflects the transaction’s rate lock when one applied, so it can differ line to line.
MidRateSourceSource of the mid-market rate the all-in rate was built from, e.g. Bloomberg.
RateLockCreatedAtISO 8601 (UTC) — when the rate lock backing this line was struck. Empty when no lock applied.
RateLockIdThe rlk_ rate lock applied to this transaction, if any.
Net / Settlement CurrencyInitiation Amount − Processing Fee, in the settlement currency.
TransactionType / TransactionStatusSee the enumerations below.
Acquirer / Acquirer ReferenceProcessing-side identifiers.
PayerIDPayer or beneficiary identifier.
Card-only fieldsPopulated when Payment Method = CARD, empty otherwise: Card Scheme, Card Last4, Card BIN, Card Country, Card Funding Type, Issuer Name, Issuer Country, Authorisation Code, ARN, 3DS Status, MCC.
Chargeback Reference / Chargeback Reason CodeReserved; empty until chargebacks are in scope.
MetaDataFree-form key=value;key=value.

Transaction types

CodeMeaningGross sign
COLLECTIONInbound customer payment+
REFUNDOutbound to a customer who previously paid
REFUND_RETURNEDRefund that failed and was returned+
PAYOUTOutbound to a beneficiary not tied to a prior collection
PAYOUT_REVERSEDPayout that bounced and was returned+
ADJUSTMENTManual correction (carries a mandatory MetaData reason)±
RESERVE_HOLD / RESERVE_RELEASEWithholding / release of a reserve / +
CHARGEBACK / CHARGEBACK_REVERSAL / SECOND_CHARGEBACKReserved — not yet in scopen/a

Transaction statuses

AUTHORISED, CAPTURED, SALE, SETTLED, REVERSED, REFUNDED, RETURNED. Lines in a settlement file are typically in a terminal state.

Example file

An abbreviated report for SubMID AcmeNGN (M1002345), settling NGN → USD. Gross is in the processing currency (NGN); the Net, fees, and totals are in the settlement currency (USD). Every row is tagged with RecordType. Card-only columns, SessionID, RateLockCreatedAt, MidRateSource, and other fields are present in the real file but omitted here for readability.

M1002345_20260416_NGN_STL000123456.csv
1RecordType,SettlementID,Company Account,Merchant Account,Merchant Name,Settlement Date,Processing Currency,Settlement Currency,AllInRate,RateSource,Gross Total,Gross Total Currency,Fees Total,Fees Total Currency,Net Settlement Amount,Net Settlement Amount Currency,Transaction Count
2HEADER,STL000123456,Acme,M1002345,AcmeNGN,2026-04-16T00:00:00Z,NGN,USD,1577.02,Bloomberg,185400,NGN,3.75,USD,113.25,USD,3
3
4RecordType,PSP Reference,Merchant Reference,Original PSP Reference,Payment Method,Booking Date,Gross,Gross Currency,Initiation Amount,Initiation Currency,Processing Fee,Fee Currency,AllInRate,RateLockId,Net,Settlement Currency,TransactionType,TransactionStatus,PayerID
5LINE,TX_9a1b2c3d,ORDER-55001,,CARD,2026-04-16T00:00:00Z,150000,NGN,94.94,USD,2.37,USD,1580,rlk_550e8400-e29b-41d4-a716-446655440001,92.57,USD,COLLECTION,SETTLED,PAYER_7781
6LINE,TX_9a1b2c3e,ORDER-55002,,MOBILE_MONEY,2026-04-16T00:00:00Z,85400,NGN,54.05,USD,1.35,USD,1580,rlk_550e8400-e29b-41d4-a716-446655440001,52.70,USD,COLLECTION,SETTLED,PAYER_7782
7LINE,TX_9a1b2c3f,ORDER-54980,TX_88f0aa12,CARD,2026-04-16T00:00:00Z,-50000,NGN,-31.99,USD,0.03,USD,1563,rlk_550e8400-e29b-41d4-a716-446655440005,-32.02,USD,REFUND,REFUNDED,PAYER_7601

Reconciliation check: the line Net values are already in the settlement currency, so they sum directly — 92.57 + 52.70 − 32.02 = 113.25 USD — to the Net Settlement Amount, the exact amount of the wire. Because each line settles at its own locked rate (the refund here used 1563, the collections 1580), you reconcile by summing the per-line Net, not by applying the header AllInRate to the gross total. The header AllInRate (1577.02) is the amount-weighted average of the line rates, so it sits between them and won’t reproduce any single line exactly.

Delivery channels

Reports are available through two channels, configured per SubMID with one channel designated as primary.

SFTP push

CrissCross uploads the file to your SFTP location at settlement time. Best for finance teams that consume files rather than call an API.

API pull

Use the settlement.created webhook as your trigger, then pull the settlement — as JSON or as the CSV file — from the API.

SFTP push

CrissCross uploads the report to your configured SFTP directory as soon as the settlement is produced. To avoid partial reads, files are written with a .processing extension and atomically renamed to .csv only once the upload is complete — so a file appearing with its final .csv name is guaranteed to be whole.

API pull

Subscribe to the settlement.created webhook and use it as the signal that a new settlement is ready, then retrieve it via the settlement endpoints:

EndpointPurpose
GET /settlementsList settlements. Filter by mid, settlement_date range, processing_currency, settlement_currency, and status. Paginated.
GET /settlements/{id}Return the header and lines as JSON, mirroring the CSV one-to-one.
GET /settlements/{id}/fileReturn the CSV file body, or a signed download URL for large files.
POST /settlements/{id}/redeliverRe-trigger SFTP delivery or the webhook (permissioned).

The settlement.created webhook fires when a settlement becomes available. Its payload carries enough to route and fetch the report:

1{
2 "event": "settlement.created",
3 "settlement_id": "STL000123456",
4 "mid": "Acme",
5 "sub_mid": "M1002345",
6 "settlement_date": "2026-04-16",
7 "processing_currency": "NGN",
8 "settlement_currency": "USD",
9 "net_settlement_amount": 113.25,
10 "file_url": "https://files.crisscross.money/settlements/STL000123456.csv"
11}

The settlement API and settlement.created webhook are being rolled out per merchant. If you need programmatic access or SFTP delivery configured for a SubMID, contact [email protected].