Viewing file: commandline.py (4.98 KB) -rw-r--r-- Select action/file-type: (+) | (+) | (+) | Code (+) | Session (+) | (+) | SDB (+) | (+) | (+) | (+) | (+) | (+) |
import argparse import shlex import sys
from copy import deepcopy
from ..config import Configuration from ..setting import BooleanSetting, ChoiceSetting, ListSetting from .base import Source
__all__ = ("CommandLineSource",)
# pylint: disable=R0201
class CommandLineSource(Source): # pylint: disable=R0913 def __init__( self, arguments=None, options=None, version=None, parser_options=None, positional=None, ): super(CommandLineSource, self).__init__()
if arguments is None: self.arguments = sys.argv[1:] elif isinstance(arguments, str): self.arguments = shlex.split(arguments) elif isinstance(arguments, (list, tuple)): self.arguments = arguments else: raise TypeError("arguments must be a string or list of strings")
self.version = version self.options = options or {} self.parser_options = parser_options or {} self.positional = positional or ()
def get_flags(self, setting): if setting.name in self.options: if "flags" in self.options[setting.name]: return self.options[setting.name]["flags"]
flags = [] flag = "--%s" % setting.name.lower().replace("_", "-") flags.append(flag) return flags
def get_action(self, setting): if isinstance(setting, BooleanSetting): return "store_false" if setting.default else "store_true" elif isinstance(setting, ListSetting): return "append" else: return "store"
# pylint: disable=W0613 def get_default(self, setting): # Caveat: Returning something other than SUPPRESS probably won't # work the way you'd think. return argparse.SUPPRESS
def get_type(self, setting): if isinstance(setting, (ListSetting, BooleanSetting)): return None elif isinstance(setting, ChoiceSetting): return setting.subtype.sanitize else: return setting.sanitize
def get_dest(self, setting): return setting.name
def get_choices(self, setting): if isinstance(setting, ChoiceSetting): return setting.choices else: return None
def get_help(self, setting): if setting.name in self.options: if "help" in self.options[setting.name]: return self.options[setting.name]["help"] return None
def get_metavar(self, setting): if setting.name in self.options: if "metavar" in self.options[setting.name]: return self.options[setting.name]["metavar"] return None
def build_argument(self, setting): flags = self.get_flags(setting) action = self.get_action(setting) default = self.get_default(setting) argtype = self.get_type(setting) dest = self.get_dest(setting) choices = self.get_choices(setting) arghelp = self.get_help(setting) metavar = self.get_metavar(setting)
argument_kwargs = { "action": action, "default": default, "dest": dest, "help": arghelp, } if argtype: argument_kwargs["type"] = argtype if choices: argument_kwargs["choices"] = choices if metavar: argument_kwargs["metavar"] = metavar
return flags, argument_kwargs
def build_parser(self, settings, manager): parser_options = deepcopy(self.parser_options) if not parser_options.get("prog") and manager: parser_options["prog"] = manager.name parser = argparse.ArgumentParser(**parser_options)
add_version = self.version is not None
for setting in settings: flags, argument_kwargs = self.build_argument(setting) parser.add_argument(*flags, **argument_kwargs)
if add_version and setting.name == "version": # Don't want to conflict with the desired setting add_version = False
if add_version: parser.add_argument( "--version", action="version", version="%(prog)s " + self.version )
if self.positional: for name, options in self.positional: parser.add_argument(name, **options)
return parser
def get_config(self, settings, manager=None, parent=None): parser = self.build_parser(settings, manager) parsed = parser.parse_args(self.arguments)
for setting in settings: if hasattr(parsed, setting.name): setting.value = getattr(parsed, setting.name)
if self.positional and manager: arguments = {} for name, _ in self.positional: if hasattr(parsed, name): arguments[name] = getattr(parsed, name) setattr(manager, "arguments", arguments)
return Configuration(settings=settings, parent=parent)
|