Accountant is a set of utilities and scripts that I've developed to allow me to do accounts from the command line. In some way it's similar to Ledger, although it's a lot simpler.
See net worth, totals, liquid and unrealised gains.
┏━━━━━━━━━━━━━━┳━━━━━━━━━━━━━┳━━━━━━━━━━━━━┳━━━━━━━━━━━━━┳━━━━━━━━━━━━━┳━━━━━━━━━━━━━━┳━━━━━━┓
┃ Account ┃ Value ┃ Illiquid ┃ Liquid ┃ Unrealised ┃ Total ┃ % Net┃
┣━━━━━━━━━━━━━━╋━━━━━━━━━━━━━╋━━━━━━━━━━━━━╋━━━━━━━━━━━━━╋━━━━━━━━━━━━━╋━━━━━━━━━━━━━━╋━━━━━━┫
┃ mybank ┃ USD 5,586.55┃ USD 2,638.50┃ USD 2,948.50┃ USD 1,205.95┃ USD 6,792.50 ┃ 63.88┃
┃ myforeignbank┃ GBP 3,000.0 ┃ GBP 0.0 ┃ GBP 3,000.0 ┃ GBP 0.0 ┃ USD 3,840.0 ┃ 36.12┃
┣━━━━━━━━━━━━━━╋━━━━━━━━━━━━━╋━━━━━━━━━━━━━╋━━━━━━━━━━━━━╋━━━━━━━━━━━━━╋━━━━━━━━━━━━━━╋━━━━━━┫
┃ Total ┃ USD 9,426.55┃ USD 2,638.50┃ USD 6,788.50┃ USD 1,205.95┃ USD 10,632.50┃ ┃
┗━━━━━━━━━━━━━━┻━━━━━━━━━━━━━┻━━━━━━━━━━━━━┻━━━━━━━━━━━━━┻━━━━━━━━━━━━━┻━━━━━━━━━━━━━━┻━━━━━━┛
Information on equities and funds in the portfolio
┏━━━━━━━┳━━━━━━━━┳━━━┳━━━━┳━━━━┳━━━━━━━┳━━━━━━┳━━━━━━━━━━┳━━━━━━━━━━━┳━━━━━━━┳━━━━━━━━━┳━━━━━━━┳━━━━━━━━┳━━━━━━━━┓
┃ Sym ┃ Price ┃ Δ ┃ Δ% ┃ $Δ ┃ # ┃ >age ┃ Cst Bas. ┃ Mkt Value ┃ Div. ┃ Gain ┃ 30d% ┃ Growth ┃ Return ┃
┣━━━━━━━╋━━━━━━━━╋━━━╋━━━━╋━━━━╋━━━━━━━╋━━━━━━╋━━━━━━━━━━╋━━━━━━━━━━━╋━━━━━━━╋━━━━━━━━━╋━━━━━━━╋━━━━━━━━╋━━━━━━━━┫
┃ MCD ┃ 153.96 ┃ 0 ┃ 0% ┃ 0 ┃ 10.00 ┃ 1963 ┃ 969.39 ┃ 1539.60 ┃ 0 ┃ 570.20 ┃ 0.89 ┃ 58.81 ┃ 58.81 ┃
┃ VTI ┃ 126.31 ┃ 0 ┃ 0% ┃ 0 ┃ 15.00 ┃ 1963 ┃ 1240.00 ┃ 1894.65 ┃ 12.34 ┃ 654.65 ┃ 0.82 ┃ 52.79 ┃ 53.79 ┃
┃ BND ┃ 81.95 ┃ 0 ┃ 0% ┃ 0 ┃ 5.00 ┃ 1963 ┃ 428.65 ┃ 409.75 ┃ 0 ┃ -18.90 ┃ -0.60 ┃ -4.40 ┃ -4.40 ┃
┣━━━━━━━╋━━━━━━━━╋━━━╋━━━━╋━━━━╋━━━━━━━╋━━━━━━╋━━━━━━━━━━╋━━━━━━━━━━━╋━━━━━━━╋━━━━━━━━━╋━━━━━━━╋━━━━━━━━╋━━━━━━━━┫
┃ Total ┃ ┃ ┃ 0% ┃ 0 ┃ 30.00 ┃ ┃ 2638.30 ┃ 3844.00 ┃ 12.33 ┃ 1205.94 ┃ 0.36 ┃ 45.71% ┃ 46.18% ┃
┗━━━━━━━┻━━━━━━━━┻━━━┻━━━━┻━━━━┻━━━━━━━┻━━━━━━┻━━━━━━━━━━┻━━━━━━━━━━━┻━━━━━━━┻━━━━━━━━━┻━━━━━━━┻━━━━━━━━┻━━━━━━━━┛
- Data is maintained in a text(json) file.
- There should be no lock-in - it should be trivial to write a script to convert to another format, ie ledger.
- Currency, i18n agnostic.
- Scriptable, extensible.
- Should be error tolerant - should help you locate data errors, but not throw annoying errors.
You use accountant by creating (or generating) an account.json file. This is simply a list of transactions and statements about your accounts.
ie:
[
{"date" : "2012-01-02", "typ" : "statement", "account" : "mybank", "balance" : 0, "currency" : "USD"}
, {"date" : "2012-01-03", "typ" : "transaction", "src" : "myjob", "dest" : "mybank", "amount" : 1000.01, "currency" : "USD"}
]
See: example json
transaction
- Parameters:
date, src, dest, amount, currency
- Events:
onTransaction
- Parameters:
statement
stock-buy, etf-buy mutfund-buy
sell, stock-sell, etf-sell, mutfund-sell
dividend
brokerage-statement
The runner iterates through the objects in the accounts file and triggers known events in the reports. A global state is passed to all reports, allowing balances etc. to be maintained.
A report is a series of event handlers that are triggered in order as the account file is traversed.
onEvent
state.banks[ID].currency
state.banks[ID].balance
state.banks[ID].last_statement
state.banks[ID].equities[TICKER].position = quantity
state.banks[ID].equities[TICKER].costbasis
state.banks[ID].equities[TICKER].dividends
There is a validation report that checks that transactions match statements.
Writing data serialisation formats is a fools game. JSON is one of the most widely used data formats, libraries exist in almost every language. It doesn't have any easy to screw-up features like significant whitespace. CSV would also be a valid choice, but we have so many different fields for different transaction types that it would end up very sparse.
The goal of the file format is to be easily read by a script, thus it should be easy to write a script to turn it into whatever format you need for another tool.
accountant.addReport(foo)
foo.onTransaction(transaction, state)