Finance
Read financial summaries and the transaction ledger, and create shareable payment links
for a sale, a debt, or a one-off wallet top-up. Everything here only ever collects money
into your own wallet - creating a payment link doesn’t move money out, so
payment_links:write isn’t a finance-write scope requiring an IP allowlist. For moving
money out, see Wallet & payouts.
Summaries and transactions
All endpoints share the prefix /v1/finance and authenticate with an API key.
finance:read grants both child read scopes.
Get a summary
GET /v1/finance/summaryQuery parameters
{
"message": "Financial summary retrieved",
"data": {
"date": "2026-01-15",
"isToday": true,
"currency": "NGN",
"walletBalance": 250000,
"salesTotal": 180000,
"pendingOrdersCount": 3,
"pendingOrdersTotal": 45000,
"expensesTotal": 20000,
"pendingDebtTotal": 12000,
"creditsTotal": 175000,
"pendingTransactionsCount": 2,
"velocityData": [
{ "intervalStart": "2026-01-15T10:00:00.000+01:00", "value": 30000 },
{ "intervalStart": "2026-01-15T11:00:00.000+01:00", "value": 45000 }
]
}
}Money fields are numeric values in the currency identified by currency. Format them in
your application using the user’s locale and the returned ISO 4217 currency code.
Each velocityData entry is a sales-total bucket. intervalStart is an ISO 8601 timestamp
with an offset. Daily summaries use hourly buckets; period summaries use daily buckets.
Passing from and to returns the same shape plus startDate, endDate, periodLabel,
and totalDays.
List transactions
GET /v1/finance/transactionsCovers every money movement recorded against the business - sales, expenses, wallet deposits/withdrawals, refunds, and more.
Query parameters
Use customer_id by itself, or use customer_email and customer_phone. Do not combine
customer_id with the email or phone filters. Customer resolution is always scoped to the
authenticated business. An unknown email or phone returns an empty transaction list.
{
"message": "Transactions retrieved",
"data": [
{
"id": "tx1a2b3c-...",
"reference": "CLV-TX-0001",
"type": "credit",
"amount": 5000,
"customer": "Ada Lovelace",
"status": "cleared",
"date": "2026-01-15",
"dateLabel": "15 Jan, 10:00 AM",
"fullDate": "2026-01-15T10:00:00.000Z",
"method": "Card",
"storeId": "st1a2b3c-...",
"customerId": "cus1a2b3c-...",
"customerEmail": "ada@example.com",
"customerPhone": "2348012345678",
"paymentLinkId": "pl1a2b3c-...",
"paymentLinkReference": "CLV-PL-0001"
}
],
"meta": { "total": 1, "page": 1, "perPage": 20, "totalPages": 1, "hasMore": false }
}Get a transaction
GET /v1/finance/transactions/:idReturns 404 not_found if the ID doesn’t belong to your business.
Requery a transaction
POST /v1/finance/transactions/:id/requeryRe-checks the transaction’s status with the payment provider and updates it if it has changed. Useful when a webhook was missed or delayed.
Generate a receipt
POST /v1/finance/transactions/:id/receipt{
"message": "Receipt generated",
"data": { "url": "https://.../receipts/tx1a2b3c.pdf" }
}Payment links
Shareable checkout links for an existing sale, an existing debt, or a one-off wallet
top-up. All endpoints share the prefix /v1/payment-links.
This is the same feature as the dashboard’s Payment links, scoped for API keys. Once created, a link is shared and paid the same way regardless of how it was created. See Checkout for the public checkout flow.
A business can select multiple checkout virtual account providers in Sales settings. The hosted checkout shows the selected providers, and Cloove randomly chooses one for each new virtual account. Leaving the selection empty uses the workspace default, so existing integrations continue to work without additional configuration.
List payment links
GET /v1/payment-linksQuery parameters
Use customer_id by itself, or use customer_email and customer_phone. Do not combine
customer_id with the email or phone filters. Customer resolution is scoped to the
authenticated business. An unknown email or phone returns an empty payment-link list.
{
"message": "Payment links retrieved",
"data": [
{
"id": "pl1a2b3c-...",
"reference": "CLV-PL-0001",
"targetType": "sale",
"targetId": "s1a2b3c4-...",
"title": null,
"amount": 15000,
"currency": "NGN",
"customerName": "Ada Lovelace",
"customerEmail": "ada@example.com",
"customerPhone": "+2348012345678",
"customerId": "cus1a2b3c-...",
"description": "Invoice INV-2026-001",
"redirectUrl": "https://merchant.example/orders/INV-2026-001",
"status": "active",
"isReusable": false,
"isStatic": false,
"expiresAt": null,
"createdAt": "2026-01-15T10:00:00.000Z"
}
],
"meta": { "total": 1, "page": 1, "perPage": 20, "totalPages": 1, "hasMore": false }
}Get a payment link
GET /v1/payment-links/:idCreate a payment link for a sale or debt
POST /v1/payment-linksCreates (or returns the existing active link for) a payment collection URL against an
existing SALE or DEBT. The amount is derived from the target’s outstanding balance -
you don’t set it directly.
Body
{
"target_type": "sale",
"target_id": "60dd38ab-85f1-4e7c-9f63-7c6072199918",
"redirect_url": "https://merchant.example/orders/INV-2026-001",
"customer": {
"name": "Ada Lovelace",
"email": "ada@example.com",
"phone_number": "+2348012345678"
}
}Response 201 Created. Send an Idempotency-Key header to avoid duplicates.
Create a wallet top-up link
POST /v1/payment-links/wallet/dynamicA one-off, amount-based link that funds your own wallet when paid. Use it for an invoice or another payment that is not tied to an existing sale.
Body
{
"title": "Consulting deposit",
"amount": 50000,
"redirect_url": "https://merchant.example/deposits/result",
"customer": {
"name": "Ada Lovelace",
"email": "ada@example.com"
}
}Response 201 Created. Send an Idempotency-Key header to avoid duplicates.
Customer identity and matching
The optional customer object supports:
Provide at least one of email or phone_number when sending customer. Cloove looks for
an active customer belonging to the authenticated business. If no customer matches, Cloove
creates one and stores its customerId on the payment link. If email and phone number match
different customers, the request fails instead of linking the payment to the wrong customer.
For sale and debt links, omitting customer keeps the customer already attached to the target.
Providing customer explicitly sets the payment link’s customer mapping.
Customer matching never crosses business boundaries. The customer fields returned on a payment
link are snapshots used to prefill checkout, while customerId is the durable customer mapping.
Cancel a payment link
DELETE /v1/payment-links/:idMarks the link CANCELLED. It stops accepting payment but is not deleted.
Redirect after checkout
When redirect_url is present, the hosted checkout redirects the payer after payment,
cancellation, or link expiry. Cloove preserves existing query parameters and adds:
For example:
https://merchant.example/orders/INV-2026-001?payment_status=paid&payment_reference=CLV-PL-0001Treat redirect parameters as user-facing navigation context, not proof of payment. Verify the
transaction using payment.received webhooks or the transaction APIs before fulfilling an order.