import argparse
from ..utils import write_yml
[docs]
class CLIArgument:
"""
Model which holds information required to define a single command-line
argument as per the
:py:class:`~argparse.ArgumentParser`'s ``add_argument()`` function API.
For more detalls, refer `official python guide \
<https://docs.python.org/3/library/argparse.html#the-add-argument-method>`_.
"""
args: list
"Arguments, as passed to the ``ArgumentParser.add_argument()`` function."
kwargs: dict
"Key-word arguments, as passed to the ``ArgumentParser.add_argument()`` "
"function."
def __init__(self, *args, **kwargs):
self.args = args
self.kwargs = kwargs
def __repr__(self):
arg_repr = ", ".join(self.args)
kwargs_repr = ", ".join(
f"{key}={repr(value)}" for key, value in self.kwargs.items()
)
return f"<CLIArgument [{', '.join([arg_repr, kwargs_repr])}]>"
[docs]
class CLICommandParser:
"""
Builds the argparser for CLI application initialisation
"""
def __init__(self, version: str = None):
"""
Instantiate CLICommandParser object.
"""
self.__parser = argparse.ArgumentParser(
formatter_class=argparse.RawTextHelpFormatter
)
self.__subparser = self.__parser.add_subparsers(
title="subcommands", required=True
)
if version:
self.__parser.add_argument(
"-V",
"--version",
action="version",
version=f"%(prog)s {version}",
)
[docs]
def create_sub_parser(
self, subparser_name, sub_command, cli_args, help=None
):
"""
Creates sub parser.
Parameters
----------
subparser_name: str
Name of the sub parser.
sub_command: func
Function associated with the sub command.
cli_args: [CLIArgument]
List of CLI arguments associated with the sub command.
help: str
Help text for the sub command.
"""
sub_p = self.__subparser.add_parser(
subparser_name,
help=help,
formatter_class=argparse.RawTextHelpFormatter,
)
sub_p.set_defaults(sub_command=sub_command)
for arg in cli_args:
sub_p.add_argument(*arg.args, **arg.kwargs)
@property
def cli_args_dict(self):
"""
Return dictionary containing CLI arguments
Returns
-------
dict
"""
cli_args = self.__parser.parse_args()
return vars(cli_args)
[docs]
def write_yml(self, path):
"""
Writes cli arguments to provided path in yaml format.
Parameters
----------
path: str
Location of config file to write to.
"""
cli_args = self.cli_args_dict
cli_args.pop("sub_command", None)
write_yml(path, cli_args)