Skip to main content
Wallet management is fundamental to financial applications. This guide shows you how to implement core wallet operations using Blnk’s ledger system.

Understanding wallet structure

In Blnk, wallets are represented as balances. Each balance tracks:
  • Balance: Current available funds
  • Credit balance: Total incoming funds
  • Debit balance: Total outgoing funds
  • Inflight balance: Funds held in pending transactions

Creating a wallet

Create a balance to represent a user’s wallet:
1

Create balance request

POST /balances
{
  "ledger_id": "ldg_123456",
  "currency": "USD",
  "identity_id": "user_abc123",
  "meta_data": {
    "wallet_type": "main",
    "user_email": "[email protected]"
  }
}
2

Response

{
  "balance_id": "bln_abc123def456",
  "ledger_id": "ldg_123456",
  "identity_id": "user_abc123",
  "balance": 0,
  "credit_balance": 0,
  "debit_balance": 0,
  "inflight_balance": 0,
  "currency": "USD",
  "created_at": "2024-01-15T10:30:00Z"
}

Making a deposit

Deposit funds from an external source into a user’s wallet:
1

Record deposit transaction

POST /transactions
{
  "amount": 100.00,
  "precision": 100,
  "reference": "dep_stripe_ch_abc123",
  "currency": "USD",
  "source": "@world",
  "destination": "bln_abc123def456",
  "description": "Stripe deposit",
  "meta_data": {
    "payment_method": "stripe",
    "charge_id": "ch_abc123"
  }
}
The @world indicator represents an external source. Blnk automatically creates this special balance if it doesn’t exist.
2

Response

{
  "transaction_id": "txn_789xyz",
  "amount": 100.00,
  "precise_amount": "10000",
  "reference": "dep_stripe_ch_abc123",
  "currency": "USD",
  "source": "bln_world_usd",
  "destination": "bln_abc123def456",
  "status": "APPLIED",
  "created_at": "2024-01-15T10:35:00Z"
}

Processing a withdrawal

Withdraw funds from a user’s wallet to an external account:
1

Record withdrawal transaction

POST /transactions
{
  "amount": 50.00,
  "precision": 100,
  "reference": "wth_bank_transfer_xyz789",
  "currency": "USD",
  "source": "bln_abc123def456",
  "destination": "@world",
  "description": "Bank withdrawal",
  "meta_data": {
    "withdrawal_method": "bank_transfer",
    "bank_account": "****1234"
  }
}
2

Check for sufficient funds

If the balance is insufficient, Blnk will reject the transaction:
{
  "error": "insufficient balance"
}
Always check the balance before attempting withdrawals in your application logic.

Transferring between wallets

Transfer funds between two user wallets:
POST /transactions
{
  "amount": 25.00,
  "precision": 100,
  "reference": "transfer_user123_to_user456",
  "currency": "USD",
  "source": "bln_abc123def456",
  "destination": "bln_xyz789ghi012",
  "description": "P2P transfer",
  "meta_data": {
    "transfer_type": "p2p",
    "sender_id": "user_123",
    "recipient_id": "user_456"
  }
}

Checking balance

Retrieve the current balance of a wallet:
1

Get balance by ID

GET /balances/bln_abc123def456
2

Response with all balance fields

{
  "balance_id": "bln_abc123def456",
  "balance": "7500",
  "credit_balance": "10000",
  "debit_balance": "2500",
  "inflight_balance": "0",
  "currency": "USD",
  "ledger_id": "ldg_123456"
}
The precise_amount values are in minor units (cents). Divide by precision (100) to get the decimal amount:
  • Balance: 7500 / 100 = $75.00
  • Credit: 10000 / 100 = $100.00
  • Debit: 2500 / 100 = $25.00

Using balance indicators

Balance indicators provide a convenient way to reference balances without knowing their IDs:
POST /transactions
{
  "amount": 100.00,
  "precision": 100,
  "reference": "dep_user_email_deposit",
  "currency": "USD",
  "source": "@world",
  "destination": "@[email protected]",
  "description": "Deposit to email-based wallet"
}
Blnk will automatically:
  1. Look for a balance with indicator @[email protected] and currency USD
  2. Create it if it doesn’t exist
  3. Use it in the transaction

Best practices

Use unique references

Always use unique transaction references to prevent duplicate transactions.

Include metadata

Store additional context in meta_data for audit trails and reconciliation.

Precision matters

Always set precision to 100 for standard currencies to handle cents accurately.

Check balances

Verify sufficient funds before processing withdrawals or transfers.

Common patterns

Multi-currency wallets

Create separate balances for each currency:
// USD wallet
POST /balances
{
  "ledger_id": "ldg_123456",
  "currency": "USD",
  "identity_id": "user_abc123"
}

// EUR wallet
POST /balances
{
  "ledger_id": "ldg_123456",
  "currency": "EUR",
  "identity_id": "user_abc123"
}

Fee handling

Use distributions to split transactions and collect fees:
POST /transactions
{
  "amount": 100.00,
  "precision": 100,
  "reference": "txn_with_fee_001",
  "currency": "USD",
  "source": "bln_sender",
  "destinations": [
    {
      "identifier": "bln_recipient",
      "distribution": "95%",
      "narration": "Transfer amount"
    },
    {
      "identifier": "bln_fee_wallet",
      "distribution": "5%",
      "narration": "Platform fee"
    }
  ],
  "description": "Transfer with 5% fee"
}

Next steps

Inflight Transactions

Learn how to hold funds for pending operations

Balance Monitoring

Set up alerts for balance changes

Build docs developers (and LLMs) love