function account_series_map(accounts, tabulation) map = {} for i=1,100 do -- we're not messing with accounts more than 100 levels deep all_handled = true for id, acct in pairs(accounts) do if not map[id] then all_handled = false if not acct.parent then map[id] = tabulation:series(acct.name) elseif map[acct.parent.accountid] then map[id] = map[acct.parent.accountid]:series(acct.name) end end end if all_handled then return map end end error("Accounts nested (at least) 100 levels deep") end function generate() year = date.now().year-4 accounts = get_accounts() t = tabulation.new(20) t:title(year .. "-" .. date.now().year .. " Quarterly Net Worth") series_map = account_series_map(accounts, t:series("Net Worth")) default_currency = get_default_currency() for month=1,20 do end_date = date.new(year, month*3-2, 1) t:label(month, tostring(end_date)) for id, acct in pairs(accounts) do series = series_map[id] if acct.type ~= account.Expense and acct.type ~= account.Income and acct.type ~= account.Trading then balance = acct:balance(end_date) multiplier = 1 if acct.security ~= default_currency then price = acct.security:closestprice(default_currency, end_date) if price == nil then --[[ -- This should contain code to warn the user that their report is missing some information --]] multiplier = 0 else multiplier = price.value end end series:value(month, balance.amount * multiplier) end end end return t end