def transform_balances(balances): """Translate a Balances entry into an uncompiled Select statement. Args: balances: An instance of a Balance object. Returns: An instance of an uncompiled Select object. """ ## FIXME: Change the aggregation rules to allow GROUP-BY not to include the ## non-aggregate ORDER-BY columns, so we could just GROUP-BY accounts here ## instead of having to include the sort-key. I think it should be fine if ## the first or last sort-order value gets used, because it would simplify ## the input statement. cooked_select = query_parser.Parser().parse(""" SELECT account, SUM({}(position)) GROUP BY account, ACCOUNT_SORTKEY(account) ORDER BY ACCOUNT_SORTKEY(account) """.format(balances.summary_func or "")) return query_parser.Select(cooked_select.targets, balances.from_clause, balances.where_clause, cooked_select.group_by, cooked_select.order_by, None, None, None, None)
def transform_journal(journal): """Translate a Journal entry into an uncompiled Select statement. Args: journal: An instance of a Journal object. Returns: An instance of an uncompiled Select object. """ cooked_select = query_parser.Parser().parse(""" SELECT date, flag, MAXWIDTH(payee, 48), MAXWIDTH(narration, 80), account, {summary_func}(position), {summary_func}(balance) {where} """.format(where=('WHERE account ~ "{}"'.format(journal.account) if journal.account else ''), summary_func=journal.summary_func or '')) return query_parser.Select(cooked_select.targets, journal.from_clause, cooked_select.where_clause, None, None, None, None, None, None)
def test_balance(self): balance = self.parse("BALANCES;") select = qc.transform_balances(balance) self.assertEqual( qp.Select([ qp.Target(qp.Column('account'), None), qp.Target(qp.Function('sum', [qp.Column('position')]), None), ], None, None, self.group_by, self.order_by, None, None, None, None), select)
def qSelect(target_spec=None, from_clause=None, where_clause=None, group_by=None, order_by=None, pivot_by=None, limit=None, distinct=None, flatten=None): "A convenience constructor for writing tests without having to provide all arguments." return qp.Select(target_spec, from_clause, where_clause, group_by, order_by, pivot_by, limit, distinct, flatten)
def test_balance_with_units_and_from(self): balance = self.parse("BALANCES AT cost FROM year = 2014;") select = qc.transform_balances(balance) self.assertEqual( qp.Select([ qp.Target(qp.Column('account'), None), qp.Target( qp.Function( 'sum', [qp.Function('cost', [qp.Column('position')])]), None), ], qp.From(qp.Equal(qp.Column('year'), qp.Constant(2014)), None, None, None), None, self.group_by, self.order_by, None, None, None, None), select)
def test_journal(self): journal = self.parse("JOURNAL;") select = qc.transform_journal(journal) self.assertEqual( qp.Select([ qp.Target(qp.Column('date'), None), qp.Target(qp.Column('flag'), None), qp.Target(qp.Function('maxwidth', [qp.Column('payee'), qp.Constant(48)]), None), qp.Target(qp.Function('maxwidth', [qp.Column('narration'), qp.Constant(80)]), None), qp.Target(qp.Column('account'), None), qp.Target(qp.Column('position'), None), qp.Target(qp.Column('balance'), None), ], None, None, None, None, None, None, None, None), select)
def test_journal_with_account_and_from(self): journal = self.parse("JOURNAL 'liabilities' FROM year = 2014;") select = qc.transform_journal(journal) self.assertEqual( qp.Select([ qp.Target(qp.Column('date'), None), qp.Target(qp.Column('flag'), None), qp.Target(qp.Function('maxwidth', [qp.Column('payee'), qp.Constant(48)]), None), qp.Target(qp.Function('maxwidth', [qp.Column('narration'), qp.Constant(80)]), None), qp.Target(qp.Column('account'), None), qp.Target(qp.Column('position'), None), qp.Target(qp.Column('balance'), None), ], qp.From(qp.Equal(qp.Column('year'), qp.Constant(2014)), None, None, None), qp.Match(qp.Column('account'), qp.Constant('liabilities')), None, None, None, None, None, None), select)