"""CLI: Show summarised information on a piggybank.""" from argparse import ArgumentParser from os.path import exists from sys import exit, stderr from piggybank import print_program_version, PIGGYBANK_FILE_EXTENSION from piggybank.cli import EPILOGUE from piggybank.currencies import CURRENCIES, DEFAULT_CURRENCY, \ BaseCurrencyError, print_supported_currencies from piggybank.piggybank import PiggyBank __all__ = ["main"] DEFAULT_COIN_CENTERING: int = 10 def print_summary(piggybank: PiggyBank, centering: int = DEFAULT_COIN_CENTERING) -> None: """Print summarised information on a piggy bank. Prints a table with totals of how much coins of which face value are in a piggy bank; A total sum converted to its currency for each face value and overall total sum in a currency of a piggy bank.""" def print_separator(left="┣", lmiddle="╋", rmiddle="╋", right="┫"): line = rmiddle.join('━' * centering for _ in range(CURRENCIES[piggybank.currency]['count'])) print(f"{left}{'━'*27}{lmiddle}{line}{right}") cc, cs, ct = piggybank.count, piggybank.sum, piggybank.total cline = "┃".join([f'{l:^{centering}}' for l in CURRENCIES[piggybank.currency]["names"]]) cline_len = len(cline) print_separator(left="┏", lmiddle="┳", rmiddle="━", right="┓") print(f"┃{'currency':^27}┃" f"{CURRENCIES[piggybank.currency]['name']:^{cline_len}}┃") print_separator(rmiddle="┳") print(f"┃{'face values':^27}┃{cline}┃") print_separator() print(f"┃{'amount':^27}┃{'┃'.join([f'{c:^{centering}}' for c in cc])}┃") print_separator() print(f"┃{'sum':^27}┃" f"{'┃'.join(['{:^{}.2f}'.format(c / 100, centering) for c in cs])}┃") print_separator(rmiddle="┻") print(f"┃{'total':^27}┃{'{:^{}.2f}'.format(ct / 100, cline_len)}┃") print_separator(left="┗", lmiddle="┻", rmiddle="━", right="┛") def print_transactions(piggybank, centering=DEFAULT_COIN_CENTERING): """Print a list of all transactions stored in a piggy bank.""" def print_separator(left="┏", middle="┳", right="┓"): line = middle.join('━' * centering for _ in range(CURRENCIES[piggybank.currency]['count'])) print(f"{left}━━━━━━━━━━━━━━━━━━━━━{middle}━━━━━{middle}{line}{right}") cline = "┃".join([f'{l:^{centering}}' for l in CURRENCIES[piggybank.currency]["names"]]) print_separator() print(f"┃{'Timestamp':^21}┃ I/O ┃{cline}┃") print_separator("┣", "╋", "┫") for tr in piggybank.transactions: coin_line = "┃".join([f'{c:^{centering}}' for c in tr.coins]) ts = tr.timestamp.replace("T", " ") print(f"┃ {ts} ┃{tr.direction:^5}┃{coin_line}┃") print_separator("┗", "┻", "┛") def main(): """An entry point for a show command.""" parser = ArgumentParser(prog="piggybank-show", description="Show information on a piggy bank.", epilog=EPILOGUE) parser.add_argument("file", type=str, help="a piggy bank file name. Missing .pb extension" "will be added") parser.add_argument("-t", "--transactions", action="store_true", help="print a list of transactions as well") parser.add_argument("-m", "--merge", action="append", type=str, metavar="FILE", help="merge multiple files to show how much do you" "have across them. They all should be of same currency") parser.add_argument("-v", "--version", action="store_true", help="show program's version and license and exit") parser.add_argument("--list-currencies", action="store_true", help="list all supported currencies and exit") args = parser.parse_args() if args.version: print_program_version() exit() if args.list_currencies: print_supported_currencies() exit() try: piggybank = PiggyBank.from_file(args.file) if args.merge: for _file in args.merge: merge_piggybank = PiggyBank.from_file(_file) piggybank += merge_piggybank print(_file) print_summary(piggybank) if args.transactions: print_transactions(piggybank) except BaseCurrencyError as err: print(f"{type(err).__name__}:", err, file=stderr) except FileNotFoundError as err: print(f"{type(err).__name__}:", f"{err} doesn't exist.", file=stderr) except Exception as err: print(f"Something went exceptionally wrong. Error:", f"{type(err).__name__}:", err, file=stderr)