sort_entries: New tool.
This commit is contained in:
parent
7baa78fe34
commit
639a41b782
2 changed files with 102 additions and 1 deletions
100
conservancy_beancount/tools/sort_entries.py
Normal file
100
conservancy_beancount/tools/sort_entries.py
Normal file
|
@ -0,0 +1,100 @@
|
|||
#!/usr/bin/env python3
|
||||
"""sort_entries.py - Consistently sort and format Beancount entries
|
||||
|
||||
This is useful to use as a preprocessing step before comparing entries with
|
||||
tools like ``diff``.
|
||||
"""
|
||||
# Copyright © 2020 Brett Smith
|
||||
#
|
||||
# This program is free software: you can redistribute it and/or modify
|
||||
# it under the terms of the GNU Affero General Public License as published by
|
||||
# the Free Software Foundation, either version 3 of the License, or
|
||||
# (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU Affero General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU Affero General Public License
|
||||
# along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
|
||||
import argparse
|
||||
import logging
|
||||
import os
|
||||
import sys
|
||||
|
||||
from pathlib import Path
|
||||
|
||||
from beancount.core import display_context as bc_dcontext
|
||||
from beancount import loader as bc_loader
|
||||
from beancount.parser import printer as bc_printer
|
||||
|
||||
from typing import (
|
||||
Hashable,
|
||||
Optional,
|
||||
Sequence,
|
||||
TextIO,
|
||||
)
|
||||
from ..beancount_types import (
|
||||
Directive,
|
||||
Entries,
|
||||
Errors,
|
||||
)
|
||||
|
||||
from .. import cliutil
|
||||
|
||||
PROGNAME = 'bean-sort'
|
||||
logger = logging.getLogger('conservancy_beancount.tools.sort_entries')
|
||||
|
||||
def parse_arguments(arglist: Optional[Sequence[str]]=None) -> argparse.Namespace:
|
||||
parser = argparse.ArgumentParser(prog=PROGNAME)
|
||||
cliutil.add_version_argument(parser)
|
||||
cliutil.add_loglevel_argument(parser)
|
||||
parser.add_argument(
|
||||
'--quiet', '-q',
|
||||
action='store_true',
|
||||
help="""Suppress Beancount errors
|
||||
""")
|
||||
parser.add_argument(
|
||||
'paths',
|
||||
metavar='PATH',
|
||||
type=Path,
|
||||
nargs=argparse.ONE_OR_MORE,
|
||||
help="""Beancount path(s) to read entries from
|
||||
""")
|
||||
return parser.parse_args(arglist)
|
||||
|
||||
def entry_sorter(entry: Directive) -> Hashable:
|
||||
type_name = type(entry).__name__
|
||||
if type_name == 'Transaction':
|
||||
return (entry.date, type_name, entry.narration, entry.payee or '') # type:ignore[attr-defined]
|
||||
else:
|
||||
return (entry.date, type_name)
|
||||
|
||||
def main(arglist: Optional[Sequence[str]]=None,
|
||||
stdout: TextIO=sys.stdout,
|
||||
stderr: TextIO=sys.stderr,
|
||||
) -> int:
|
||||
args = parse_arguments(arglist)
|
||||
cliutil.set_loglevel(logger, args.loglevel)
|
||||
|
||||
entries: Entries = []
|
||||
errors: Errors = []
|
||||
for path in args.paths:
|
||||
new_entries, new_errors, _ = bc_loader.load_file(path)
|
||||
entries.extend(new_entries)
|
||||
errors.extend(new_errors)
|
||||
entries.sort(key=entry_sorter)
|
||||
if not args.quiet:
|
||||
for error in errors:
|
||||
bc_printer.print_error(error, file=stderr)
|
||||
dcontext = bc_dcontext.DisplayContext()
|
||||
dcontext.set_commas(True)
|
||||
bc_printer.print_entries(entries, dcontext, file=stdout)
|
||||
return os.EX_DATAERR if errors and not args.quiet else os.EX_OK
|
||||
|
||||
entry_point = cliutil.make_entry_point(__name__, PROGNAME)
|
||||
|
||||
if __name__ == '__main__':
|
||||
exit(entry_point())
|
3
setup.py
3
setup.py
|
@ -5,7 +5,7 @@ from setuptools import setup
|
|||
setup(
|
||||
name='conservancy_beancount',
|
||||
description="Plugin, library, and reports for reading Conservancy's books",
|
||||
version='1.11.1',
|
||||
version='1.12.0',
|
||||
author='Software Freedom Conservancy',
|
||||
author_email='info@sfconservancy.org',
|
||||
license='GNU AGPLv3+',
|
||||
|
@ -40,6 +40,7 @@ setup(
|
|||
'accrual-report = conservancy_beancount.reports.accrual:entry_point',
|
||||
'assemble-audit-reports = conservancy_beancount.tools.audit_report:entry_point',
|
||||
'balance-sheet-report = conservancy_beancount.reports.balance_sheet:entry_point',
|
||||
'bean-sort = conservancy_beancount.tools.sort_entries:entry_point',
|
||||
'extract-odf-links = conservancy_beancount.tools.extract_odf_links:entry_point',
|
||||
'fund-report = conservancy_beancount.reports.fund:entry_point',
|
||||
'ledger-report = conservancy_beancount.reports.ledger:entry_point',
|
||||
|
|
Loading…
Reference in a new issue