From bebc817d19b27f608182b1853a812bc3d9141209 Mon Sep 17 00:00:00 2001 From: Tyler Goodlet Date: Wed, 26 Jul 2023 12:13:54 -0400 Subject: [PATCH] Partition ledger data frames by `bs_mktid` Since some backends are going to have the issue of supporting multiple venues for a given "position distinguishing instrument", like IB, we can't presume that every `Position` can be uniquely keyed by a `MktPair.fqme` (since the venue part can change and still be the same "pair" relationship in accounting terms) so instead presume the "backend system's market id" is the unique key (at least for now) instead of the fqme. More practically we use the `bs_mktid` to groupby-partition the per pair DFs from the trades ledger and attempt to scan-match the input fqme (in `ledger disect` cli) against the fqme column values set. --- piker/accounting/calc.py | 2 +- piker/accounting/cli.py | 22 ++++++++++++++++++++-- 2 files changed, 21 insertions(+), 3 deletions(-) diff --git a/piker/accounting/calc.py b/piker/accounting/calc.py index d86ad98c..941fddb4 100644 --- a/piker/accounting/calc.py +++ b/piker/accounting/calc.py @@ -428,7 +428,7 @@ def open_ledger_dfs( # break up into a frame per mkt / fqme dfs: dict[str, pl.DataFrame] = ldf.partition_by( - 'fqme', + 'bs_mktid', as_dict=True, ) diff --git a/piker/accounting/cli.py b/piker/accounting/cli.py index 753e6513..4106cb7e 100644 --- a/piker/accounting/cli.py +++ b/piker/accounting/cli.py @@ -19,6 +19,7 @@ CLI front end for trades ledger and position tracking management. ''' from __future__ import annotations +from pprint import pformat from rich.console import Console @@ -264,7 +265,7 @@ def disect( # ledger dfs groupby-partitioned by fqme dfs: dict[str, pl.DataFrame] - # actual ledger ref filled in with all txns + # actual ledger instance ldgr: TransactionLedger pl.Config.set_tbl_cols(16) @@ -277,7 +278,24 @@ def disect( ): # look up specific frame for fqme-selected asset - df = dfs[fqme] + if (df := dfs.get(fqme)) is None: + mktids2fqmes: dict[str, list[str]] = {} + for bs_mktid in dfs: + df: pl.DataFrame = dfs[bs_mktid] + fqmes: pl.Series[str] = df['fqme'] + uniques: list[str] = fqmes.unique() + mktids2fqmes[bs_mktid] = set(uniques) + if fqme in uniques: + break + print( + f'No specific ledger for fqme={fqme} could be found in\n' + f'{pformat(mktids2fqmes)}?\n' + f'Maybe the `{brokername}` backend uses something ' + 'else for its `bs_mktid` then the `fqme`?\n' + 'Scanning for matches in unique fqmes per frame..\n' + ) + + # :pray: assert not df.is_empty() # TODO: we REALLY need a better console REPL for this