def compile_args(self): """Generator to convert pending arguments into CliCommandArgument objects. """ for name, details in self._arg_tree.items(): if self._is_bool(name): if self._request_param['name'].endswith('patch_parameter'): self._help( name, "Specify either 'true' or 'false' to update the property." ) else: details['options']['action'] = 'store_true' self._help(name, "True if flag present.") elif self._is_list(name): details['options']['nargs'] = '+' elif self._is_datetime(name): details['options']['type'] = validators.datetime_format self._help(name, "Expected format is an ISO-8601 timestamp.") elif self._is_duration(name): details['options']['type'] = validators.duration_format self._help(name, "Expected format is an ISO-8601 duration.") elif self._is_silent(name): import argparse from azure.cli.core.commands.parameters import IgnoreAction details['options']['nargs'] = '?' details['options']['help'] = argparse.SUPPRESS details['options']['required'] = False details['options']['action'] = IgnoreAction yield (name, CliCommandArgument(dest=name, **details['options']))
def test_override_argtype_with_argtype(self): existing_options_list = ('--default', '-d') arg = CliArgumentType(options_list=existing_options_list, validator=None, completer='base', help='base', required=True) overriding_argtype = CliArgumentType(options_list=('--overridden', ), validator='overridden', completer=None, overrides=arg, help='overridden', required=CliArgumentType.REMOVE) self.assertEqual(overriding_argtype.settings['validator'], 'overridden') self.assertEqual(overriding_argtype.settings['completer'], None) self.assertEqual(overriding_argtype.settings['options_list'], ('--overridden', )) self.assertEqual(overriding_argtype.settings['help'], 'overridden') self.assertEqual(overriding_argtype.settings['required'], CliArgumentType.REMOVE) cmd_arg = CliCommandArgument(dest='whatever', argtype=overriding_argtype, help=CliArgumentType.REMOVE) self.assertFalse('required' in cmd_arg.options) self.assertFalse('help' in cmd_arg.options)
def _process_options(self): """Process the request options parameter to expose as arguments.""" for param in [o for o in self._options_attrs if o not in IGNORE_OPTIONS]: options = {} options['required'] = False options['arg_group'] = 'Pre-condition and Query' if param in ['if_modified_since', 'if_unmodified_since']: options['type'] = validators.datetime_format if param in FLATTEN_OPTIONS: for f_param, f_docstring in FLATTEN_OPTIONS[param].items(): options['default'] = None options['help'] = f_docstring options['options_list'] = [arg_name(f_param)] options['validator'] = validators.validate_options yield (f_param, CliCommandArgument(f_param, **options)) else: options['default'] = getattr(self._options_model, param) options['help'] = find_param_help(self._options_model, param) options['options_list'] = [arg_name(param)] yield (param, CliCommandArgument(param, **options))
def extract_args_from_signature(operation): """ Extracts basic argument data from an operation's signature and docstring """ from azure.cli.core.commands import CliCommandArgument args = [] try: # only supported in python3 - falling back to argspec if not available sig = inspect.signature(operation) args = sig.parameters except AttributeError: sig = inspect.getargspec(operation) #pylint: disable=deprecated-method args = sig.args arg_docstring_help = _option_descriptions(operation) for arg_name in [a for a in args if not a in EXCLUDED_PARAMS]: try: # this works in python3 default = args[arg_name].default required = default == inspect.Parameter.empty #pylint: disable=no-member except TypeError: arg_defaults = (dict( zip(sig.args[-len(sig.defaults):], sig.defaults)) if sig.defaults else {}) default = arg_defaults.get(arg_name) required = arg_name not in arg_defaults action = 'store_' + str(not default).lower() if isinstance( default, bool) else None try: default = ( default if default != inspect._empty #pylint: disable=protected-access, no-member else None) except AttributeError: pass yield (arg_name, CliCommandArgument( arg_name, options_list=['--' + arg_name.replace('_', '-')], required=required, default=default, help=arg_docstring_help.get(arg_name), action=action))
def _load_transformed_arguments(self, handler): """Load all the command line arguments from the request parameters. :param func handler: The operation function. """ from azure.cli.core.commands.parameters import file_type from argcomplete.completers import FilesCompleter, DirectoriesCompleter self.parser = BatchArgumentTree(self.validator, self.silent) self._load_options_model(handler) for arg in extract_args_from_signature(handler): arg_type = find_param_type(handler, arg[0]) if arg[0] == self._options_param: for option_arg in self._process_options(): yield option_arg elif arg_type.startswith("str or"): docstring = find_param_help(handler, arg[0]) choices = [] values_index = docstring.find(' Possible values include') if values_index >= 0: choices = docstring[values_index + 25:].split(', ') choices = [c for c in choices if c != "'unmapped'"] docstring = docstring[0:values_index] yield (arg[0], CliCommandArgument(arg[0], options_list=[arg_name(arg[0])], required=False, default=None, choices=choices, help=docstring)) elif arg_type.startswith( ":class:"): # TODO: could add handling for enums param_type = class_name(arg_type) self.parser.set_request_param(arg[0], param_type) param_model = _load_model(param_type) self._flatten_object(arg[0], param_model) for flattened_arg in self.parser.compile_args(): yield flattened_arg param = 'json_file' docstring = "A file containing the {} specification in JSON format. " \ "If this parameter is specified, all '{} Arguments'" \ " are ignored.".format(arg[0].replace('_', ' '), group_title(arg[0])) yield (param, CliCommandArgument(param, options_list=[arg_name(param)], required=False, default=None, type=file_type, completer=FilesCompleter(), help=docstring)) elif arg[0] not in self.ignore: yield arg return_type = find_return_type(handler) if return_type == 'Generator': param = 'destination' docstring = "The path to the destination file or directory." yield (param, CliCommandArgument( param, options_list=[arg_name(param)], required=True, default=None, completer=DirectoriesCompleter(), type=file_type, validator=validators.validate_file_destination, help=docstring)) if return_type == 'None' and handler.__name__.startswith('get'): self.head_cmd = True if self.confirmation: param = CONFIRM_PARAM_NAME docstring = 'Do not prompt for confirmation.' yield (param, CliCommandArgument(param, options_list=['--yes', '-y'], required=False, action='store_true', help=docstring))
def extract_args_from_signature(operation, no_wait_param=None): """ Extracts basic argument data from an operation's signature and docstring no_wait_param: SDK parameter which disables LRO polling. For now it is 'raw' """ from azure.cli.core.commands import CliCommandArgument args = [] try: # only supported in python3 - falling back to argspec if not available sig = inspect.signature(operation) args = sig.parameters except AttributeError: sig = inspect.getargspec(operation) #pylint: disable=deprecated-method args = sig.args arg_docstring_help = _option_descriptions(operation) excluded_params = list(EXCLUDED_PARAMS) if no_wait_param in excluded_params: excluded_params.remove(no_wait_param) found_no_wait_param = False for arg_name in [a for a in args if not a in excluded_params]: try: # this works in python3 default = args[arg_name].default required = default == inspect.Parameter.empty #pylint: disable=no-member except TypeError: arg_defaults = (dict( zip(sig.args[-len(sig.defaults):], sig.defaults)) if sig.defaults else {}) default = arg_defaults.get(arg_name) required = arg_name not in arg_defaults action = 'store_' + str(not default).lower() if isinstance( default, bool) else None try: default = ( default if default != inspect._empty #pylint: disable=protected-access, no-member else None) except AttributeError: pass #improve the naming to 'no_wait' if arg_name == no_wait_param: if not isinstance(default, bool): raise ValueError("The type of '{}' must be boolean to enable for no_wait".format(no_wait_param)) #pylint: disable=line-too-long found_no_wait_param = True options_list = ['--no-wait'] help_str = 'do not wait for the long running operation to finish' else: options_list = ['--' + arg_name.replace('_', '-')] help_str = arg_docstring_help.get(arg_name) yield (arg_name, CliCommandArgument(arg_name, options_list=options_list, required=required, default=default, help=help_str, action=action)) if no_wait_param and not found_no_wait_param: raise ValueError("Command authoring error: unable to enable no-wait option. Operation '{}' does not have a '{}' parameter.".format(operation, no_wait_param)) #pylint: disable=line-too-long