def main(argv: t.Optional[t.List[str]] = None) -> None: from argparse import _ # 1st parser parser = argparse.ArgumentParser(add_help=False) parser.add_argument( "-h", "--help", action="store_true", help=_("show this help message and exit"), ) parser.add_argument("--fn", required=False, choices=[x.__name__ for x in [f, g]]) args, rest_args = parser.parse_known_args(argv) if args.fn is None and args.help: parser.print_help() parser.exit() if args.help: rest_args.append("-h") fn = globals()[args.fn] # 2nd parser parser = argparse.ArgumentParser() Injector(fn).inject(parser, help_default=None) args = parser.parse_args(rest_args) params = vars(args).copy() print(fn(**params))
def hello_send(message: Message): import shlex text = message.body["text"] parser = Parser(prog="$hello") Injector(hello).inject(parser) argv = shlex.split(text.split("$hello", 1)[1], posix=True) try: args = parser.parse_args(argv) except Exit as e: texts = [] if e.args[0]: texts.append(e.args[0]) texts.append(parser.format_help()) new_line = "\n" message.send(f"""\ ``` {new_line.join(texts).strip(new_line)} ```""") return params = vars(args).copy() with contextlib.redirect_stdout(StringIO()) as o: hello(**params) output = o.getvalue() if output.strip(): message.send(output)
def use_gencode(): from codeobject import Module m = Module() argparse = m.import_("argparse") with m.def_("create_parser"): parser = m.let("parser", argparse.ArgumentParser(prog="app.py")) subparsers = m.let( "subparsers", parser.add_subparsers(title="subcommands", required=True, dest="subcommand"), ) m.sep() for fn in [hello, byebye]: m.stmt(f"# for {fn.__name__}") sub_parser = m.let( "sub_parser", subparsers.add_parser(fn.__name__, help=UnRepr(f"{fn.__name__}.__doc__")), ) Injector(fn).inject(sub_parser, callback=m.stmt) m.stmt(sub_parser.set_defaults(subcommand=fn)) m.sep() m.return_(parser) print(m)
def use_gencode(): from codeobject import Module, codeobject @codeobject def ArgumentParser(m: Module, name: str) -> Module: pass m = Module() parser = m.let("parser", ArgumentParser(prog="app.py")) Injector(hello).inject(parser, callback=m.stmt) print(m)
def run(self, argv=None, *, ignore_logging=False, description=None): parser = self.create_parser(argv=argv, description=description) subparsers = parser.add_subparsers() subparsers.required = True for fn in self.functions: sub_parser = subparsers.add_parser(fn.__name__) Injector(fn).inject(sub_parser) sub_parser.set_defaults(sub_command=fn) args = parser.parse_args(argv) return args
def register(self, fn: t.Callable[..., t.Any]) -> t.Callable[..., t.Any]: sub_parser = self.subparsers.add_parser( fn.__name__, help=_get_summary(fn), formatter_class=self.parser.formatter_class, ) # NOTE: positional arguments are treated as component Injector(fn).inject(sub_parser, ignore_arguments=True) sub_parser.set_defaults(subcommand=fn) return fn
def main(): from monogusa.web.codegen import _codeobject as codeobject from monogusa.web.codegen._codeobject import Module from monogusa.cli import runtime from handofcats.injector import Injector m = Module() # hmm m.stmt("from codegen import hello, byebye") with m.def_("create_parser"): argparse = m.import_("argparse") driver = runtime.Driver( parser=m.let("parser", argparse.ArgumentParser())) driver.subparsers = m.let("subparsers", driver.subparsers) if driver.subparsers.required: m.stmt("{}.required = True", driver.subparsers) m.sep() scanned = runtime.scan_module() for fn in scanned.commands: sub_parser = m.let( "sub_parser", driver.subparsers.add_parser(fn.__name__, help=runtime._get_summary(fn)), ) # NOTE: positional arguments are treated as component Injector(fn).inject(sub_parser, ignore_arguments=True, callback=m.stmt) m.stmt("{}.set_defaults(subcommand={})", sub_parser, fn.__name__) sub_parser.set_defaults(subcommand=fn) m.sep() m.return_(driver.parser) with m.def_("main"): parser = m.let("parser", codeobject.Symbol("create_parser")()) args = m.let("args", parser.parse_args()) params = m.let("params", codeobject.Symbol("vars")(args)) action = m.let("action", params.pop("subcommand")) m.sep() m.stmt("# TODO positionals") m.sep() m.stmt("{}(**params)", action) with m.if_("__name__ == '__main__'"): m.stmt("main()") print(m)
def use_normal(): import argparse parser = argparse.ArgumentParser(prog="app.py") subparsers = parser.add_subparsers(title="subcommands", required=True, dest="subcommand") r = [] for fn in [hello, byebye]: sub_parser = subparsers.add_parser(fn.__name__, help=fn.__doc__) Injector(fn).inject(sub_parser, do=id) r.append(sub_parser) print(parser.format_help()) for sp in r: print(sp.format_help())
def run(self, m: M, parser: t.Any, argv=None, *, ignore_logging=False): subparsers = m.let("subparsers", parser.add_subparsers()) m.setattr(subparsers, "required", True) # xxx: m.sep() for original_fn in self.functions: fn = m.let("fn", m.symbol(original_fn)) sub_parser = m.let( "sub_parser", subparsers.add_parser(m.getattr(fn, "__name__"), help=m.getattr(fn, "__doc__")), ) Injector(original_fn).inject(sub_parser, callback=m.stmt) m.stmt(sub_parser.set_defaults(sub_command=fn)) m.sep() args = parser.parse_args(argv) return m.return_(args)
async def hello(ctx: commands.Context, *argv: str, **kwargs): parser = Parser(prog="$hello") Injector(_hello).inject(parser) output_list = [] try: with contextlib.redirect_stdout(StringIO()) as o: args = parser.parse_args(argv) params = vars(args).copy() _hello(**params) except Exit as e: output_list.append(str(e)) output = o.getvalue() if output.strip(): output_list.append(output) new_line = "\n" await ctx.send(f"""\ ``` {new_line.join(output_list).strip(new_line)} ```""")
def register(self, fn: t.Callable) -> t.Callable: sub_parser = self.subparsers.add_parser(fn.__name__, help=inspect.getdoc(fn)) Injector(fn).inject(sub_parser) sub_parser.set_defaults(action=fn) return fn
from handofcats.parsers.expose import create_parser from handofcats.injector import Injector def hello(*, name: str) -> None: print(f"hello {name}") parser = create_parser(hello) Injector(hello).inject(parser) print(parser)
def use_normal(): import argparse parser = argparse.ArgumentParser(prog="app.py") Injector(hello).inject(parser, callback=id) print(parser.format_help())
import argparse from handofcats.injector import Injector def add(*, x: int, y: int) -> int: return x + y def hello(*, name: str = "world") -> None: print(f"hello {name}") parser = argparse.ArgumentParser() sparsers = parser.add_subparsers(required=True, title="subcommands") Injector(add).inject(sparsers.add_parser("add")) Injector(hello).inject(sparsers.add_parser("hello")) # parser.parse_args(["add", "-h"]) # parser.parse_args(["hello", "-h"]) parser.parse_args(["-h"])
return DATABASE_URL @fixture def engine(database_url: str): # TODO: teardown return sqlalchemy.create_engine(database_url, connect_args={"check_same_thread": False}) def init_db(engine: Engine, *, debug: bool, message: str = "hmm"): """init tables""" if debug: log.instance_logger(engine, echoflag=True) metadata.create_all(bind=engine) engine.dispose() print(f"** init_db {debug=} {message=} **") from handofcats.injector import Injector import argparse parser = argparse.ArgumentParser() injector = Injector(init_db) injector.inject(parser, ignore_arguments=True) parser.print_help() resolve_args = import_symbol("bootstrap.py:resolve_args", here=__file__) args = resolve_args(init_db) init_db(*args, debug=True)