Robot Framework
argumentresolver.py
Go to the documentation of this file.
1 # Copyright 2008-2015 Nokia Networks
2 # Copyright 2016- Robot Framework Foundation
3 #
4 # Licensed under the Apache License, Version 2.0 (the "License");
5 # you may not use this file except in compliance with the License.
6 # You may obtain a copy of the License at
7 #
8 # http://www.apache.org/licenses/LICENSE-2.0
9 #
10 # Unless required by applicable law or agreed to in writing, software
11 # distributed under the License is distributed on an "AS IS" BASIS,
12 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 # See the License for the specific language governing permissions and
14 # limitations under the License.
15 
16 from robot.errors import DataError
17 from robot.utils import is_string, is_dict_like, split_from_equals
18 from robot.variables import is_dict_variable
19 
20 from .argumentvalidator import ArgumentValidator
21 
22 
24 
25  def __init__(self, argspec, resolve_named=True,
26  resolve_variables_until=None, dict_to_kwargs=False):
27  self._named_resolver_named_resolver = NamedArgumentResolver(argspec) \
28  if resolve_named else NullNamedArgumentResolver()
29  self._variable_replacer_variable_replacer = VariableReplacer(resolve_variables_until)
30  self._dict_to_kwargs_dict_to_kwargs = DictToKwargs(argspec, dict_to_kwargs)
31  self._argument_validator_argument_validator = ArgumentValidator(argspec)
32 
33  def resolve(self, arguments, variables=None):
34  positional, named = self._named_resolver_named_resolver.resolve(arguments, variables)
35  positional, named = self._variable_replacer_variable_replacer.replace(positional, named, variables)
36  positional, named = self._dict_to_kwargs_dict_to_kwargs.handle(positional, named)
37  self._argument_validator_argument_validator.validate(positional, named,
38  dryrun=variables is None)
39  return positional, named
40 
41 
43 
44 
45  def __init__(self, argspec):
46  self._argspec_argspec = argspec
47 
48  def resolve(self, arguments, variables=None):
49  positional = []
50  named = []
51  for arg in arguments:
52  if is_dict_variable(arg):
53  named.append(arg)
54  elif self._is_named_is_named(arg, named, variables):
55  named.append(split_from_equals(arg))
56  elif named:
57  self._raise_positional_after_named_raise_positional_after_named()
58  else:
59  positional.append(arg)
60  return positional, named
61 
62  def _is_named(self, arg, previous_named, variables=None):
63  name, value = split_from_equals(arg)
64  if value is None:
65  return False
66  if variables:
67  try:
68  name = variables.replace_scalar(name)
69  except DataError:
70  return False
71  spec = self._argspec_argspec
72  return bool(previous_named or
73  spec.var_named or
74  name in spec.positional_or_named or
75  name in spec.named_only)
76 
78  raise DataError("%s '%s' got positional argument after named arguments."
79  % (self._argspec_argspec.type.capitalize(), self._argspec_argspec.name))
80 
81 
83 
84  def resolve(self, arguments, variables=None):
85  return arguments, {}
86 
87 
89 
90  def __init__(self, argspec, enabled=False):
91  self._maxargs_maxargs = argspec.maxargs
92  self._enabled_enabled = enabled and bool(argspec.var_named)
93 
94  def handle(self, positional, named):
95  if self._enabled_enabled and self._extra_arg_has_kwargs_extra_arg_has_kwargs(positional, named):
96  named = positional.pop().items()
97  return positional, named
98 
99  def _extra_arg_has_kwargs(self, positional, named):
100  if named or len(positional) != self._maxargs_maxargs + 1:
101  return False
102  return is_dict_like(positional[-1])
103 
104 
106 
107  def __init__(self, resolve_until=None):
108  self._resolve_until_resolve_until = resolve_until
109 
110  def replace(self, positional, named, variables=None):
111  # `variables` is None in dry-run mode and when using Libdoc.
112  if variables:
113  positional = variables.replace_list(positional, self._resolve_until_resolve_until)
114  named = list(self._replace_named_replace_named(named, variables.replace_scalar))
115  else:
116  # If `var` isn't a tuple, it's a &{dict} variables.
117  named = [var if isinstance(var, tuple) else (var, var) for var in named]
118  return positional, named
119 
120  def _replace_named(self, named, replace_scalar):
121  for item in named:
122  for name, value in self._get_replaced_named_get_replaced_named(item, replace_scalar):
123  if not is_string(name):
124  raise DataError('Argument names must be strings.')
125  yield name, value
126 
127  def _get_replaced_named(self, item, replace_scalar):
128  if not isinstance(item, tuple):
129  return replace_scalar(item).items()
130  name, value = item
131  return [(replace_scalar(name), replace_scalar(value))]
def __init__(self, argspec, resolve_named=True, resolve_variables_until=None, dict_to_kwargs=False)
def _is_named(self, arg, previous_named, variables=None)
def __init__(self, argspec)
:type argspec: :py:class:robot.running.arguments.ArgumentSpec
def replace(self, positional, named, variables=None)
def split_from_equals(string)
Definition: escaping.py:105
def is_dict_like(item)
Definition: robottypes.py:72
def is_dict_variable(string)
Definition: search.py:46