Overview
Account Statements (also called Ledger Account Statements) show the complete transaction history for any ledger account, including opening balance, all debits and credits during the period, and closing balance.Permission required:
ledger:readStatements can be generated for any ledger account: member savings, bank accounts, loans, revenue, expenses, assets, or liabilities.API Endpoint
Get account statements:| Field | Type | Required | Description |
|---|---|---|---|
accountIds | string[] | Yes | Array of ledger account UUIDs |
from | string (ISO date) | Yes | Statement period start date |
to | string (ISO date) | Yes | Statement period end date |
option | enum | Yes | Statement option: 'all', 'current', 'period', 'custom' |
excludeZeroTransactionAccounts | boolean | No | If true, exclude accounts with no transactions in period. Defaults to false. |
| Option | Description |
|---|---|
'all' | All transactions from account creation to to date |
'current' | Current period (typically current month) |
'period' | Specific date range from from to to |
'custom' | Custom date range (same as 'period') |
Response Structure
| Field | Type | Description |
|---|---|---|
accountId | string | Ledger account UUID |
accountName | string | Account name (e.g., “Jane Smith - Savings”) |
accountRole | string | Account role (SAVINGS, CASH, LOAN_RECEIVABLE, etc.) |
accountType | string | Account type (ASSET, LIABILITY, EQUITY, REVENUE, EXPENSE) |
accountStatus | string | ”Active” or “Inactive” |
periodStart | string (ISO datetime) | Statement period start |
periodEnd | string (ISO datetime) | Statement period end |
rows | array | Transaction rows (includes opening balance if applicable) |
totalDebit | number | Sum of all debits in period (excludes opening balance) |
totalCredit | number | Sum of all credits in period (excludes opening balance) |
closingBalance | number | Ending balance |
| Field | Type | Description |
|---|---|---|
date | string (ISO datetime) | Transaction date |
description | string | Transaction description (from journal entry kind) |
debit | number | null | Debit amount (null if credit transaction) |
credit | number | null | Credit amount (null if debit transaction) |
balance | number | Running balance after this transaction |
Understanding Debits and Credits
CRITICAL: Debit and credit directions depend on account type. For member savings accounts (LIABILITY type), the directions are opposite of what you might expect: For SAVINGS accounts (LIABILITY type):- CREDIT = Increase (deposits add to balance) ✓
- DEBIT = Decrease (withdrawals, loan disbursements reduce balance) ✓
- DEBIT = Increase (money in) ✓
- CREDIT = Decrease (money out) ✓
- DEBIT = Increase (loan granted) ✓
- CREDIT = Decrease (payment received) ✓
- CREDIT = Increase (income earned) ✓
- DEBIT = Decrease (rare) ✓
- DEBIT = Increase (expense incurred) ✓
- CREDIT = Decrease (rare) ✓
How It Works
The account statements endpoint:-
Validates account IDs
- Checks that all accountIds exist in organization
- Returns 404 if any account not found
-
For each account, gets journal entries in date range
- Filters by transactionDate between
fromandto - Only includes POSTED entries (excludes DRAFT)
- Excludes reversed entries (reversedEntryId = null)
- Sorts by transaction date ascending
- Filters by transactionDate between
-
Finds opening balance
- Looks for journal entry with transactionDate = null (opening balance entry)
- Calculates balance after that entry
- Includes as first row if appropriate
-
Creates transaction rows
- For each journal entry:
- Extracts debit or credit amount for this account
- Gets running balance from ledger
- Formats description from journal entry kind
- For each journal entry:
-
Calculates totals
- Sums all debits (excludes opening balance row)
- Sums all credits (excludes opening balance row)
- Gets closing balance from last row
-
Filters zero-transaction accounts (optional)
- If
excludeZeroTransactionAccounts = true - Removes accounts where no debits or credits occurred in period
- If
Common Use Cases
Member Savings Statements
Generate statements for all members:- Opening balance at start of quarter
- All deposits made
- All withdrawals (if any)
- Loan disbursements from their savings
- Dividend distributions
- Closing balance
Bank Account Reconciliation
Generate Agatabo bank statement:- Download bank statement from bank
- Generate Agatabo statement for same period
- Compare line by line:
- Agatabo DEBITS = Bank deposits (money in)
- Agatabo CREDITS = Bank withdrawals (money out)
- Identify differences:
- Uncleared checks
- Bank fees not yet recorded
- Deposits in transit
- Errors
Loan Account Analysis
Track loan principal changes:- Opening balance: Principal at start of period
- DEBITS: Additional loans granted (increases receivable)
- CREDITS: Payments received (decreases receivable)
- Closing balance: Outstanding principal
Revenue/Expense Statements
Track interest income:- All interest earned during year
- Breakdown by transaction date
- Total interest income (totalCredit for revenue accounts)
Statement Options Explained
option: 'all'
- Includes ALL transactions from account creation to
todate - Ignores
fromparameter periodStartset to account creation date or earliest transaction- Use for: Complete account history
option: 'current'
- Typically current month (implementation may vary)
- Uses
fromandtodates provided - Use for: Monthly statements
option: 'period'
- Specific date range from
fromtoto - Use for: Custom periods (quarterly, annual, etc.)
option: 'custom'
- Same as
'period' - Specific date range from
fromtoto
Bulk Statement Generation
Generate statements for all member savings accounts: Step 1: Get all member savings account IDs- Generate PDF statements for printing
- Create CSV exports for analysis
- Send email statements to members
- Display in web interface
Filtering Zero-Transaction Accounts
Problem: When generating bulk member statements, some members may have no activity during the period. Including them creates unnecessary empty statements. Solution: UseexcludeZeroTransactionAccounts: true
Example:
Opening Balance Calculation
Opening balance appears as first row if:- Account has an opening balance entry (journal entry with transactionDate = null)
- Statement includes the first dated transaction for this account
- Opening balance entry exists (from January 1)
- But statement doesn’t include first dated transaction (which was in January)
- So opening balance row is NOT included
- Instead, first row shows balance as of June 1
option: 'all' includes all transactions from account creation:
- Opening balance entry exists
- First dated transaction is included
- Opening balance row appears
Transaction Descriptions
Description field comes from journal entrykind field, formatted for readability:
| Journal Entry Kind | Description |
|---|---|
| SAVINGS_DEPOSIT | Savings Deposit |
| LOAN_DISBURSEMENT | Loan Disbursement |
| LOAN_PAYMENT | Loan Payment |
| LOAN_PENALTY | Loan Penalty |
| EXPENSE_PAYMENT | Expense Payment |
| DIVIDEND_DISTRIBUTION | Dividend Distribution |
| RESERVE_TOP_UP | Reserve Top Up |
| BANK_CHARGE | Bank Charge |
| PERIOD_CLOSE | Period Close |
Best Practices
Generating account statements:For members:
- ✅ Generate quarterly statements for all active members
- ✅ Use
excludeZeroTransactionAccounts: trueto skip inactive accounts - ✅ Print and distribute at member meetings for transparency
- ✅ Verify spot-check statements against deposit records
- ✅ Generate bank statements monthly after downloading bank records
- ✅ Use exact date range matching bank statement
- ✅ Document all differences (uncleared checks, bank fees, etc.)
- ✅ Post adjusting entries before closing period
- ✅ Use
option: 'all'for complete account history - ✅ Use
option: 'period'for specific date ranges - ✅ Export to CSV for spreadsheet analysis
- ✅ Compare period-over-period to identify trends
- ✅ Member savings statements contain sensitive data
- ✅ Only generate for authorized personnel
- ✅ Don’t email unencrypted statements
- ✅ Hand-deliver printed statements to members
- ✅ Store exports in password-protected folders
Troubleshooting
Q: Balance doesn’t match what I expect A: Check:- Correct account selected? (Names can be similar)
- Date range includes all expected transactions?
- Compare to deposit/withdrawal records
- Verify with Balance Sheet total for all member savings
- Transaction date outside selected date range
- Transaction posted to different account by mistake
- Transaction in closed period (check earlier date ranges)
- Journal entry reversed or deleted (check audit logs)
- Verify member actually has savings account created
- Search by partial name (account name format: ” - Savings”)
- Check that account is active (inactive accounts may be hidden)
- Use GET /ledger-accounts?role=SAVINGS to list all
- Check if prior periods reconciled correctly
- Generate statement for prior period to trace error
- Verify opening balance entry (transactionDate = null) is correct
- May need adjusting journal entry
- LIABILITY accounts INCREASE with CREDIT
- LIABILITY accounts DECREASE with DEBIT
Example: Monthly Member Statements
Scenario: Generate statements for all members for June 2026 Step 1: Get member savings account IDsRelated Topics
Ledger Accounts
Understanding chart of accounts
Journal Entries
Transaction details behind statements
Monthly Closing Checklist
Reconciliation and closing procedures
Understanding Double-Entry
Accounting principles for statements