# Demat Escrow API > Secret-key API reference for Demat Escrow — customers, holds, checkout, wallets, payouts, and webhooks. - [Introduction](https://docs.usedemat.com/index.md): Integrate Demat Escrow with the secret key API: customers, checkout, holds, release, and payouts. - [How it works](https://docs.usedemat.com/guides/how-it-works.md): End to end escrow lifecycle: create customers or guest payers, fund a hold, release or refund, then pay out. - [Authentication](https://docs.usedemat.com/guides/authentication.md): Authenticate secret key requests with Bearer sk_test_ or sk_live_ keys. - [API basics](https://docs.usedemat.com/guides/api-basics.md): Base URL, environments, request format, response envelope, and money units. - [Fees](https://docs.usedemat.com/guides/fees.md): Provider, Demat platform, and optional merchant fees on collections, transfers, and NUBAN deposits. - [Pagination](https://docs.usedemat.com/guides/pagination.md): List endpoints use limit and offset with a pagination object in the response. - [Errors](https://docs.usedemat.com/guides/errors.md): HTTP status codes, error envelope, and common error.code values. - [Idempotency](https://docs.usedemat.com/guides/idempotency.md): Required Idempotency-Key header on POST routes that move money. - [Rate limits](https://docs.usedemat.com/guides/rate-limits.md): Per merchant quotas, rate limit headers, and how to handle HTTP 429. - [Webhooks](https://docs.usedemat.com/guides/webhooks.md): HMAC-SHA512 signed event deliveries to your webhookUrl. - [Callback URL](https://docs.usedemat.com/guides/callback-url.md): Browser return URL after checkout. Not confirmation of payment. - [List customers](https://docs.usedemat.com/api-reference/customers/list-customers.md): Page through customers on this merchant account, including walletId and live balances. account is null until you provision a NUBAN with POST /wallets. - [Create a customer](https://docs.usedemat.com/api-reference/customers/create-a-customer.md): Create a customer on this merchant account. This is identity only, not KYC, not a bank account. Returns firstName, lastName, email, phone, walletId, balances.available 0, balances.held 0, and account null. A zero balance wallet row is created in the background so you can later lock funds or provisio… - [Get a customer](https://docs.usedemat.com/api-reference/customers/get-a-customer.md): Fetch one customer: identity, walletId, balances.available / balances.held, and account if a NUBAN exists. - [Delete a customer](https://docs.usedemat.com/api-reference/customers/delete-a-customer.md): Permanently delete a customer. Allowed only when they have no provisioned NUBAN (`account` is null) and they are not payer, payee, or party on any escrow. Otherwise 409 CUSTOMER_HAS_ACCOUNT or CUSTOMER_HAS_ESCROW. The empty wallet row is removed with them. No webhook. - [Update a customer](https://docs.usedemat.com/api-reference/customers/update-a-customer.md): Update firstName, lastName, and/or phone. Email cannot be changed. omit it. Returns the same customer object as GET. - [List escrows](https://docs.usedemat.com/api-reference/escrows/list-escrows.md): Page through holds. Filter by status or customerId (payer or payee). Each item includes parties, remainingAmount, releasedAmount, and refundedAmount. - [Create an escrow](https://docs.usedemat.com/api-reference/escrows/create-an-escrow.md): Create a hold with one payer and one payee. Payer may be a registered customerId or a guest { email, name?, phone? }. Payee must be a registered customerId. Your reference must be unique. Default status is awaiting_funding. No money is locked. Pass checkout true to also return a checkout URL. Pass d… - [Get an escrow](https://docs.usedemat.com/api-reference/escrows/get-an-escrow.md): Fetch one escrow: status, parties, amount, remainingAmount still held, releasedAmount, refundedAmount, feeAmount, cancelledReason if cancelled, and timestamps. - [Cancel an unfunded escrow](https://docs.usedemat.com/api-reference/escrows/cancel-an-unfunded-escrow.md): Kill an unfunded hold (awaiting_funding only). No money moves. Reason is stored as cancelledReason. Webhook: escrow.cancelled. If the payer still completes an old checkout after this, that money credits the payer’s available. It does not reopen the hold. After funding, use refund instead. - [Get the dispute on an escrow](https://docs.usedemat.com/api-reference/escrows/get-the-dispute-on-an-escrow.md): Fetch the dispute on this hold. Returns the open dispute if one exists, otherwise the latest resolved dispute. 404 if this escrow has never had a dispute. Use this when you have escrowId and need disputeId, status, or resolution. - [Open a dispute on a held escrow](https://docs.usedemat.com/api-reference/escrows/open-a-dispute-on-a-held-escrow.md): Freeze remaining held funds. Allowed on held or partially_released. One open dispute per hold. Status becomes disputed. release and refund are blocked until you resolve. openedBy is your label (we do not check it is the payer or payee). Webhook: dispute.opened. - [Resolve a dispute by release, refund, or split](https://docs.usedemat.com/api-reference/escrows/resolve-a-dispute-by-release-refund-or-split.md): Settle an open dispute and move the remaining held funds. action=release sends remaining to the payee’s available. action=refund sends remaining to the payer’s available. action=split requires releaseAmount + refundAmount to equal remaining held. The dispute becomes resolved. You get dispute.resolve… - [Refund held funds](https://docs.usedemat.com/api-reference/escrows/refund-held-funds.md): Registered payer: return held funds to their available immediately. Guest payer: start a provider refund; escrow stays held with pendingProviderRefund until refund.processed, then liability → clearing and escrow.refunded (sandbox auto-completes). Only from held or partially_released. Omit amount to… - [Release held funds](https://docs.usedemat.com/api-reference/escrows/release-held-funds.md): Move held funds to the payee’s available balance, not their bank. Only from held or partially_released. Omit amount to release everything still held. A partial release leaves remainingAmount on the hold. Webhook: escrow.released or escrow.partially_released. Blocked while disputed. Resolve the dispu… - [Get a public checkout session](https://docs.usedemat.com/api-reference/checkout/get-a-public-checkout-session.md): Guest checkout read for hosted checkout pages. No secret key. Returns status, amount, currency, merchant.businessName, merchant.businessLogo, optional escrow description, and paymentUrl while pending. Read-only. confirm payment via webhooks, not the browser redirect. - [List checkout sessions](https://docs.usedemat.com/api-reference/checkout/list-checkout-sessions.md): Page through checkout sessions on this merchant account. Filter by status, escrowId, or customerId. Each item includes checkoutId, checkoutUrl, paymentId, and status. Use this when you did not store checkoutId from the create response or payment.pending. - [Create a checkout session](https://docs.usedemat.com/api-reference/checkout/create-a-checkout-session.md): Start hosted checkout. Pass escrowId XOR customerId. EscrowId funds an awaiting_funding hold (amount and currency must match). A second POST for that same unfunded hold returns the existing pending session. It does not start another charge. Same Idempotency-Key + same body replays the first response… - [Get a checkout session](https://docs.usedemat.com/api-reference/checkout/get-a-checkout-session.md): Fetch one checkout session you created, including checkoutUrl. - [List transactions](https://docs.usedemat.com/api-reference/transactions/list-transactions.md): Page through customer money activity for this merchant. Filter with customerId, type, direction, relatedId, startDate, and endDate. Each row is one customer’s view of an event (wallet credit, escrow funded/released/refunded, withdrawal). - [Export transactions](https://docs.usedemat.com/api-reference/transactions/export-transactions.md): Export the same filtered statement as CSV or PDF. Pass format=csv (default) or format=pdf. Up to 5000 rows. - [Get a transaction](https://docs.usedemat.com/api-reference/transactions/get-a-transaction.md): Fetch one ledger event and every customer entry on it. Releases include both payer and payee. - [List wallets](https://docs.usedemat.com/api-reference/wallets/list-wallets.md): Page through wallets. Filter by customerId. Each item includes walletId, balances, and account if a NUBAN exists. - [Provision a customer NUBAN wallet](https://docs.usedemat.com/api-reference/wallets/provision-a-customer-nuban-wallet.md): Verify the customer’s BVN (name must match) and assign a NUBAN if they do not already have one. Creating a customer already created a zero-balance wallet row. this call attaches the account. Test secret keys get a dummy Test Bank number. Live inbound transfers to that NUBAN credit available only; th… - [Get a wallet and balances](https://docs.usedemat.com/api-reference/wallets/get-a-wallet-and-balances.md): Fetch one wallet: available/held balances and optional virtual-account details. - [Simulate a NUBAN credit](https://docs.usedemat.com/api-reference/wallets/simulate-a-nuban-credit.md): Simulate an inbound NUBAN credit. Test secret keys only. Credits available only. same as a live dedicated-account transfer. Does not lock a hold. Send naira (200 for ₦200). Webhook: wallet.credited. - [List withdrawals](https://docs.usedemat.com/api-reference/payouts/list-withdrawals.md): Page through transfers you initiated. Filter by status or customerId. - [Send a customer’s available balance to a bank account](https://docs.usedemat.com/api-reference/payouts/send-a-customer’s-available-balance-to-a-bank-account.md): Send a customer’s available balance to a bank account. We find the customer, check available, resolve the account name from accountNumber and bankCode, then send. Destination is not saved. Not escrow release. Webhooks: withdrawal.created, withdrawal.processing, then withdrawal.completed or withdrawa… - [Get a withdrawal](https://docs.usedemat.com/api-reference/payouts/get-a-withdrawal.md): Fetch one transfer: status (processing, completed, failed), amount, destination last4, and failureReason if it failed. - [Quote transaction fees](https://docs.usedemat.com/api-reference/fees/quote-transaction-fees.md): Quote provider, Demat platform, and optional merchant fees for a collection, transfer, or NUBAN deposit. For collection/transfer pass the business amount. Fees are added on top. For deposit pass the gross inbound amount. NetAmount is credited to the wallet. See Fees. - [Verify a bank account](https://docs.usedemat.com/api-reference/identity/verify-a-bank-account.md): Resolve a NUBAN and return the account name. Not attached to a customer. The account is not stored. Use this to preview a name before POST /withdrawals. - [List supported banks](https://docs.usedemat.com/api-reference/identity/list-supported-banks.md): List Nigerian banks. Cache this. Use code as bankCode when resolving an account or sending a withdrawal. - [Look up NIN or BVN](https://docs.usedemat.com/api-reference/identity/look-up-nin-or-bvn.md): Look up a NIN or BVN and return name details. Not attached to a customer. The number is not stored. This is not KYC on a customer record. use it when you need the name on your side. Provisioning a NUBAN still verifies BVN itself on POST /wallets. ## OpenAPI Specs - [openapi](/openapi.json) This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.