From 2ec43338f50ff03bb2d5dfd245985a2c71ae2fb5 Mon Sep 17 00:00:00 2001 From: Christian Heller Date: Wed, 19 Mar 2025 10:24:07 +0100 Subject: [PATCH] Refactor ledger management out of Server class. --- src/run.py | 58 +++++++++++++++++++++++++++++++----------------------- 1 file changed, 33 insertions(+), 25 deletions(-) diff --git a/src/run.py b/src/run.py index d840ebe..91079d7 100755 --- a/src/run.py +++ b/src/run.py @@ -391,15 +391,15 @@ class Handler(PlomHttpHandler): self.redirect(redir_target) def post_file_action(self, file_prefixed: str) -> None: - """Based on file_prefixed name, trigger .server.load or .save.""" + """Based on file_prefixed name, trigger .server.ledger.(load|save).""" if file_prefixed == f'{PREFIX_FILE}load': - self.server.load() + self.server.ledger.load() elif file_prefixed == f'{PREFIX_FILE}save': - self.server.save() + self.server.ledger.save() def post_edit(self) -> Path: """Based on postvars, edit targeted Booking.""" - booking = self.server.bookings[int(self.path_toks[2])] + booking = self.server.ledger.bookings[int(self.path_toks[2])] new_lines = [] if self.pagename == EDIT_STRUCT: line_keys = self.postvars.keys_prefixed('line_') @@ -432,21 +432,21 @@ class Handler(PlomHttpHandler): else: # edit_raw new_lines += [DatLine(line) for line in self.postvars.first('booking').splitlines()] - new_id = self.server.rewrite_booking(booking.id_, new_lines) + new_id = self.server.ledger.rewrite_booking(booking.id_, new_lines) return Path('/bookings').joinpath(f'{new_id}') def post_ledger_action(self) -> Path: - """Parse postvar to call .server.(move|copy|add_empty_new)_booking.""" + """Call .server.ledger.(move|copy|add_empty_new)_booking.""" if 'add_booking' in self.postvars.as_dict: - id_ = self.server.add_empty_booking() + id_ = self.server.ledger.add_empty_booking() else: keys_prefixed = self.postvars.keys_prefixed(PREFIX_LEDGER) action, id_str = keys_prefixed[0].split('_', maxsplit=2)[1:] id_ = int(id_str) if action.startswith('move'): - id_ = self.server.move_booking(id_, action == 'moveup') + id_ = self.server.ledger.move_booking(id_, action == 'moveup') return Path(self.path).joinpath(f'#{id_}') - id_ = self.server.copy_booking(id_) + id_ = self.server.ledger.copy_booking(id_) return Path(EDIT_STRUCT).joinpath(f'{id_}') def do_GET(self) -> None: @@ -456,7 +456,7 @@ class Handler(PlomHttpHandler): self.redirect( Path('/').joinpath(EDIT_STRUCT).joinpath(self.path_toks[2])) return - ctx = {'tainted': self.server.tainted, 'path': self.path} + ctx = {'tainted': self.server.ledger.tainted, 'path': self.path} if self.pagename == 'balance': self.get_balance(ctx) elif self.pagename.startswith(PREFIX_EDIT): @@ -469,17 +469,17 @@ class Handler(PlomHttpHandler): def get_balance(self, ctx) -> None: """Display tree of calculated Accounts over .bookings[:up_incl+1].""" id_ = int(self.params.first('up_incl') or '-1') - ctx['roots'] = [ac for ac in self.server.accounts.values() + ctx['roots'] = [ac for ac in self.server.ledger.accounts.values() if not ac.parent] - ctx['valid'] = self.server.bookings_valid_up_incl(id_) - ctx['booking'] = self.server.bookings[id_] + ctx['valid'] = self.server.ledger.bookings_valid_up_incl(id_) + ctx['booking'] = self.server.ledger.bookings[id_] ctx['path_up_incl'] = f'{self.path_toks[1]}?up_incl=' self._send_rendered('balance', ctx) def get_edit(self, ctx, raw: bool) -> None: """Display edit form for individual Booking.""" id_ = int(self.path_toks[2]) - booking = self.server.bookings[id_] + booking = self.server.ledger.bookings[id_] observed_tree: list[dict[str, Any]] = [] for full_path in sorted(booking.account_changes.keys()): parent_children: list[dict[str, Any]] = observed_tree @@ -491,9 +491,9 @@ class Handler(PlomHttpHandler): break if already_registered: continue - self.server.ensure_account(path) - before = self.server.accounts[path].get_wealth(id_ - 1) - after = self.server.accounts[path].get_wealth(id_) + self.server.ledger.ensure_account(path) + before = self.server.ledger.accounts[path].get_wealth(id_ - 1) + after = self.server.ledger.accounts[path].get_wealth(id_) direct_target = full_path == path diff = { cur: amt for cur, amt in (after - before).moneys.items() @@ -518,36 +518,44 @@ class Handler(PlomHttpHandler): ctx['id'] = id_ ctx['dat_lines'] = [dl if raw else dl.as_dict for dl in booking.booked_lines] - ctx['valid'] = self.server.bookings_valid_up_incl(id_) + ctx['valid'] = self.server.ledger.bookings_valid_up_incl(id_) if not raw: - ctx['all_accounts'] = sorted(self.server.accounts.keys()) + ctx['all_accounts'] = sorted(self.server.ledger.accounts.keys()) self._send_rendered(EDIT_RAW if raw else EDIT_STRUCT, ctx) def get_ledger(self, ctx: dict[str, Any], raw: bool) -> None: """Display ledger of all Bookings.""" - ctx['dat_lines'] = self.server.dat_lines + ctx['dat_lines'] = self.server.ledger.dat_lines self._send_rendered(LEDGER_RAW if raw else LEDGER_STRUCT, ctx) class Server(PlomHttpServer): """Extends parent by loading .dat file into database for Handler.""" + + def __init__(self, path_dat: Path, *args, **kwargs) -> None: + super().__init__(PATH_TEMPLATES, (SERVER_HOST, SERVER_PORT), Handler) + self.ledger = Ledger(path_dat) + + +class Ledger: + """Collection of DatLines, and Accounts, Bookings derived from them.""" accounts: dict[str, Account] bookings: list[Booking] dat_lines: list[DatLine] initial_gap_lines: list[DatLine] - def __init__(self, path_dat: Path, *args, **kwargs) -> None: - super().__init__(PATH_TEMPLATES, (SERVER_HOST, SERVER_PORT), Handler) + def __init__(self, path_dat: Path) -> None: self._path_dat = path_dat self.load() def load(self) -> None: - """Read into ledger file at .path_dat.""" - self.dat_lines = [ + """(Re-)read ledger from file at ._path_dat.""" + self.accounts, self.bookings, self.initial_gap_lines = {}, [], [] + self.initial_gap_lines: list[DatLine] = [] # TODO: fix duplicate booking + self.dat_lines: list[DatLine] = [ DatLine(line) for line in self._path_dat.read_text(encoding='utf8').splitlines()] self.last_save_hash = self._hash_dat_lines() - self.bookings, self.initial_gap_lines = [], [] booked: list[DatLine] = [] gap_lines: list[DatLine] = [] booking: Optional[Booking] = None -- 2.30.2