Refactor CLI implementation: add help callback and improve help handling; update setup.py dependencies
This commit is contained in:
parent
c9176dbbce
commit
37eaee3dbe
@ -1,7 +1,12 @@
|
||||
from cli import CLI
|
||||
from .cli import CLI
|
||||
|
||||
def help_text():
|
||||
return [
|
||||
"%bold%%cyan%nut CLI ... you expected a help menu? cute :3%reset%"
|
||||
]
|
||||
|
||||
def main():
|
||||
cli = CLI("nut")
|
||||
cli = CLI(help_callback=help_text)
|
||||
|
||||
cli.command("run") \
|
||||
.flag("debug", "d") \
|
||||
@ -12,17 +17,13 @@ def main():
|
||||
|
||||
return cli.run()
|
||||
|
||||
def cmd_run(subcommands, flags):
|
||||
print("RUN")
|
||||
print("sub:", subcommands)
|
||||
print("flags:", flags)
|
||||
def cmd_run(args, flags):
|
||||
print("RUN", args, flags)
|
||||
return 0
|
||||
|
||||
def cmd_build(subcommands, flags):
|
||||
print("BUILD")
|
||||
print("sub:", subcommands)
|
||||
print("flags:", flags)
|
||||
def cmd_build(args, flags):
|
||||
print("BUILD", args, flags)
|
||||
return 0
|
||||
|
||||
if __name__ == "__main__":
|
||||
raise SystemExit(main())
|
||||
raise SystemExit(main())
|
||||
|
||||
61
nut/cli.py
61
nut/cli.py
@ -1,46 +1,78 @@
|
||||
import argparse
|
||||
from colorama import Fore, Style, init
|
||||
|
||||
init(autoreset=True)
|
||||
|
||||
class CLI:
|
||||
def __init__(self, prog="nut"):
|
||||
self.parser = argparse.ArgumentParser(prog=prog)
|
||||
self.subparsers = self.parser.add_subparsers(dest="command", required=True)
|
||||
def __init__(self, prog="nut", help_callback=None):
|
||||
self.parser = argparse.ArgumentParser(prog=prog, add_help=False)
|
||||
self.subparsers = self.parser.add_subparsers(dest="command")
|
||||
|
||||
self.help_callback = help_callback
|
||||
|
||||
self.parser.add_argument("-h", "--help", action="store_true")
|
||||
|
||||
def command(self, name):
|
||||
parser = self.subparsers.add_parser(name)
|
||||
|
||||
parser = self.subparsers.add_parser(name, add_help=False)
|
||||
cmd = _Command(parser)
|
||||
return cmd
|
||||
|
||||
def run(self):
|
||||
args = self.parser.parse_args()
|
||||
|
||||
# extract structured data
|
||||
sub_args = getattr(args, "_args", [])
|
||||
if getattr(args, "help", False) or not getattr(args, "command", None):
|
||||
if self.help_callback:
|
||||
for line in self.help_callback():
|
||||
print(self._color(line))
|
||||
else:
|
||||
self.parser.print_help()
|
||||
return 0
|
||||
|
||||
args_list = getattr(args, "_args", [])
|
||||
|
||||
flags = {
|
||||
k: v for k, v in vars(args).items()
|
||||
if k not in ("command", "func", "_args")
|
||||
if k not in ("command", "func", "_args", "help")
|
||||
}
|
||||
|
||||
return args.func(sub_args, flags)
|
||||
return args.func(args_list, flags)
|
||||
|
||||
def _color(self, text: str) -> str:
|
||||
mapping = {
|
||||
"%red%": Fore.RED,
|
||||
"%green%": Fore.GREEN,
|
||||
"%yellow%": Fore.YELLOW,
|
||||
"%blue%": Fore.BLUE,
|
||||
"%magenta%": Fore.MAGENTA,
|
||||
"%cyan%": Fore.CYAN,
|
||||
"%white%": Fore.WHITE,
|
||||
"%reset%": Style.RESET_ALL,
|
||||
"%bold%": Style.BRIGHT,
|
||||
}
|
||||
|
||||
for key, value in mapping.items():
|
||||
text = text.replace(key, value)
|
||||
|
||||
return text
|
||||
|
||||
class _Command:
|
||||
def __init__(self, parser):
|
||||
self.parser = parser
|
||||
self.parser.set_defaults(func=self._missing)
|
||||
|
||||
# default catch-all args
|
||||
self.parser.add_argument("_args", nargs="*")
|
||||
self.parser.add_argument("-h", "--help", action="store_true")
|
||||
|
||||
def arg(self, name, **kwargs):
|
||||
self.parser.add_argument(name, **kwargs)
|
||||
return self
|
||||
|
||||
def flag(self, name, short=None):
|
||||
flags = [f"--{name}"]
|
||||
opts = [f"--{name}"]
|
||||
if short:
|
||||
flags.append(f"-{short}")
|
||||
opts.append(f"-{short}")
|
||||
|
||||
self.parser.add_argument(*flags, action="store_true")
|
||||
self.parser.add_argument(*opts, action="store_true")
|
||||
return self
|
||||
|
||||
def handle(self, func):
|
||||
@ -48,4 +80,5 @@ class _Command:
|
||||
return self
|
||||
|
||||
def _missing(self, *_):
|
||||
raise RuntimeError("No handler defined for command")
|
||||
raise RuntimeError("No handler defined")
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user