Get the history of a balance
List the money movements recorded against one balance: top-ups, booking debits and refunds, newest first.
/api/v1/balances/{balance_id}/historyEach entry has a source. transactions are the authoritative balance movements: sum only these for reconciliation. flight_balance_operations and hotel_balance_operations are audit records of one booking (initial debit, exchange fee, adjustment, refund); a single action produces both a transaction and an operation. eSIM orders and topups have no audit source: their debits are transactions.
type filters on the type of the entry and is exact and case sensitive: DEBIT matches transactions (upper case) and debit matches operations (lower case). Paging is built from the newest 500 entries of each source, so older entries are not reachable: pagination.total counts the matching entries, but follow has_more to know whether another page can be served.
In the sandbox the answer is always empty. On live a balance_id that is not a balance of your agency answers balance_not_found.
curl 'https://api.fx-port.com/api/v1/balances/db002f7a-c136-4f32-b19d-38a2542f2af9/history?limit=5' \
-H "Authorization: Bearer fxp_test_YOUR_KEY"{
"environment": "sandbox",
"success": true,
"data": [],
"pagination": {
"page": 1,
"limit": 5,
"total": 0,
"total_pages": 0,
"hasMore": false,
"has_more": false
},
"meta": {
"agencyId": "0b1c2d3e-4f50-4a6b-8c7d-9e0f1a2b3c4d",
"agency_id": "0b1c2d3e-4f50-4a6b-8c7d-9e0f1a2b3c4d",
"environment": "sandbox",
"financialOperationsEnabled": false,
"financial_operations_enabled": false,
"message": "Sandbox bookings skip debits, refunds, transactions, payouts, and balance operations."
}
}{
"environment": "live",
"success": true,
"data": [
{
"source": "transactions",
"id": "3e8b1c02-d7a4-4f5e-9b2a-1c0d8e7f3a91",
"type": "CREDIT",
"amount": 2500,
"currency": "DZD",
"description": "Balance top-up",
"balanceId": "db002f7a-c136-4f32-b19d-38a2542f2af9",
"balance_id": "db002f7a-c136-4f32-b19d-38a2542f2af9",
"createdAt": "2026-10-11T09:15:00.000000+00:00",
"created_at": "2026-10-11T09:15:00.000000+00:00"
},
{
"source": "flight_balance_operations",
"id": "658185df-234c-43ba-8175-ba9a5abe6007",
"type": "debit",
"amount": 87.5,
"currency": "DZD",
"description": "Exchange fee debit for flight booking Y7PAEU",
"bookingRecordId": "711371c3-00aa-4be2-b790-9f0ca2ccfdb7",
"booking_record_id": "711371c3-00aa-4be2-b790-9f0ca2ccfdb7",
"createdAt": "2026-10-09T14:30:00.000000+00:00",
"created_at": "2026-10-09T14:30:00.000000+00:00"
},
{
"source": "transactions",
"id": "31936df0-299d-429e-b0f5-056a6c0587cc",
"type": "DEBIT",
"amount": 4925.44,
"currency": "DZD",
"description": "Booking confirmation: flight Y7PAEU (ALG → ORN)",
"balanceId": "db002f7a-c136-4f32-b19d-38a2542f2af9",
"balance_id": "db002f7a-c136-4f32-b19d-38a2542f2af9",
"createdAt": "2026-10-01T15:42:34.272792+00:00",
"created_at": "2026-10-01T15:42:34.272792+00:00"
}
],
"pagination": {
"page": 1,
"limit": 20,
"total": 3,
"total_pages": 1,
"hasMore": false,
"has_more": false
},
"meta": {
"agencyId": "0b1c2d3e-4f50-4a6b-8c7d-9e0f1a2b3c4d",
"agency_id": "0b1c2d3e-4f50-4a6b-8c7d-9e0f1a2b3c4d",
"balanceId": "db002f7a-c136-4f32-b19d-38a2542f2af9",
"balance_id": "db002f7a-c136-4f32-b19d-38a2542f2af9",
"balanceCurrency": "DZD",
"balance_currency": "DZD",
"environment": "live"
}
}Request
Path parameters
balance_idstring (uuid)requiredThe id of a balance returned by GET /.
Query parameters
date_fromstringInclusive start. Any ISO 8601 spelling is read: a date (2026-07-01 or 20260701, taken as 00:00:00 UTC) or a datetime (2026-07-01T10:30:00Z) with 1 to 9 fraction digits and an offset written Z, +01:00 or +0100. A datetime without an offset is read as UTC. Years 1900 to 2200. In a URL write a + as %2B.
At most 40 characters.
date_tostringInclusive end, in the same spellings as date_from. A bare date means the end of that day (23:59:59.999999 UTC). It must not be before date_from.
At most 40 characters.
fromstringdeprecatedLegacy name, still accepted. Use date_from instead.
Previous name of date_from. It still works, with the same spellings, and the response carries a deprecated_field warning.
At most 40 characters.
from_datestringdeprecatedLegacy name, still accepted. Use date_from instead.
Previous name of date_from. It still works, with the same spellings, and the response carries a deprecated_field warning.
At most 40 characters.
tostringdeprecatedLegacy name, still accepted. Use date_to instead.
Previous name of date_to. It still works, with the same spellings, and the response carries a deprecated_field warning.
At most 40 characters.
to_datestringdeprecatedLegacy name, still accepted. Use date_to instead.
Previous name of date_to. It still works, with the same spellings, and the response carries a deprecated_field warning.
At most 40 characters.
typestringKeep only entries of this type. Exact and case sensitive: CREDIT, DEBIT or REFUND for transactions; credit, debit or refund for operations.
At most 32 characters.
pageintegerThe page, starting at 1 (at most 10000). An empty value means not sent.
Between 1 and 10000. Default 1.
limitintegerEntries per page, from 1 to 100. An empty value means not sent.
Between 1 and 100. Default 20.
Response
200A page of movements.
successbooleantrue when the history was returned.
dataarray of objectThe movements of this page, newest first. Always empty in the sandbox.
ShowHide 12 attributes
sourcestringWhere the entry comes from. transactions are the authoritative balance movements; the two *_balance_operations sources are audit records per booking.
One of transactions, flight_balance_operations, hotel_balance_operations.
idstring (uuid)Id of the entry.
typestringThe kind of movement. transactions use upper case, *_balance_operations lower case.
One of CREDIT, DEBIT, REFUND, credit, debit, refund.
amountnumberThe amount, always positive: type tells the direction.
currencystringThe currency of the balance.
descriptionstringnullableA label of the movement, usually with the booking reference.
balanceIdstring (uuid)deprecatedLegacy name, still accepted. Use balance_id instead.
transactions only. The balance the movement was recorded against. The older name of balance_id: same value, use balance_id.
balance_idstring (uuid)transactions only. The balance the movement was recorded against. The snake_case twin of balanceId, with the same value: use this name.
bookingRecordIdstring (uuid)deprecatedLegacy name, still accepted. Use booking_record_id instead.
*_balance_operations only. The internal id of the booking, to match it with the account history. The older name of booking_record_id: same value, use booking_record_id.
booking_record_idstring (uuid)*_balance_operations only. The internal id of the booking, to match it with the account history. The snake_case twin of bookingRecordId, with the same value: use this name.
createdAtstringdeprecatedLegacy name, still accepted. Use created_at instead.
When the movement was recorded: ISO 8601, UTC. The older name of created_at: same value, use created_at.
created_atstringWhen the movement was recorded: ISO 8601, UTC. The snake_case twin of createdAt, with the same value: use this name.
paginationobjectWhere this page sits in the list.
ShowHide 6 attributes
pageintegerThe page returned.
limitintegerThe page size used.
totalintegerNumber of matching entries. Only the newest ones can be paged to (see the endpoint): follow has_more, not total.
total_pagesintegerNumber of pages: total divided by limit, rounded up. Absent when the count is not available.
hasMorebooleandeprecatedLegacy name, still accepted. Use has_more instead.
true when another page can be served. The older name of has_more: same value, use has_more.
has_morebooleantrue when another page can be served. The snake_case twin of hasMore, with the same value: use this name.
metaobjectFacts about the answer.
ShowHide 10 attributes
agencyIdstring (uuid)deprecatedLegacy name, still accepted. Use agency_id instead.
The id of your agency, resolved from the key. The older name of agency_id: same value, use agency_id.
agency_idstring (uuid)The id of your agency, resolved from the key. The snake_case twin of agencyId, with the same value: use this name.
environmentstringThe environment of the key that made the call: sandbox for fxp_test_ keys, live for fxp_live_ keys. Present in every JSON body.
One of sandbox, live.
balanceIdstring (uuid)deprecatedLegacy name, still accepted. Use balance_id instead.
Live only. The balance of the history. The older name of balance_id: same value, use balance_id.
balance_idstring (uuid)Live only. The balance of the history. The snake_case twin of balanceId, with the same value: use this name.
balanceCurrencystringdeprecatedLegacy name, still accepted. Use balance_currency instead.
Live only. The currency of the balance. The older name of balance_currency: same value, use balance_currency.
balance_currencystringLive only. The currency of the balance. The snake_case twin of balanceCurrency, with the same value: use this name.
financialOperationsEnabledbooleandeprecatedLegacy name, still accepted. Use financial_operations_enabled instead.
Sandbox only, always false. The older name of financial_operations_enabled: same value, use financial_operations_enabled.
financial_operations_enabledbooleanSandbox only, always false. The snake_case twin of financialOperationsEnabled, with the same value: use this name.
messagestringSandbox only: why data is empty.
Errors
| Status | Code | Example message |
|---|---|---|
| 400 | invalid_date | Date parameters must be ISO-8601 values, for example 2026-05-08 or 2026-05-08T10:30:00Z. |
| 400 | invalid_date_range | date_from must not be after date_to. |
| 400 | agency_id_not_allowed | External API keys resolve agency_id automatically; do not send agency_id as a query parameter. |
| 404 | balance_not_found | No balance found for ID 'db002f7a-c136-4f32-b19d-38a2542f2af9'. |
| 422 | validation_error | Input should be less than or equal to 100 |
| 503 | service_overloaded | The service is temporarily overloaded; retry after the time given in the Retry-After header. |
The shape of the error body depends on the endpoint. See Errors for every shape and code.