erroneus star arguments warning

This commit is contained in:
Dave Halter
2014-06-07 13:10:19 +02:00
parent 62db176e5e
commit c8b7d79b54
3 changed files with 25 additions and 14 deletions

View File

@@ -16,7 +16,8 @@ CODES = {
'type-error-too-few-arguments': (6, TypeError, None), 'type-error-too-few-arguments': (6, TypeError, None),
'type-error-keyword-argument': (7, TypeError, None), 'type-error-keyword-argument': (7, TypeError, None),
'type-error-multiple-values': (8, TypeError, None), 'type-error-multiple-values': (8, TypeError, None),
'type-error-star-star-mapping': (9, TypeError, None), 'type-error-star-star': (9, TypeError, None),
'type-error-star': (9, TypeError, None),
} }

View File

@@ -75,7 +75,7 @@ def get_params(evaluator, func, var_args):
for param in func.params: for param in func.params:
param_dict[str(param.get_name())] = param param_dict[str(param.get_name())] = param
# There may be calls, which don't fit all the params, this just ignores it. # There may be calls, which don't fit all the params, this just ignores it.
va = _unpack_var_args(evaluator, var_args, func.params) va = _unpack_var_args(evaluator, var_args, func)
var_arg_iterator = common.PushBackIterator(iter(va)) var_arg_iterator = common.PushBackIterator(iter(va))
non_matching_keys = [] non_matching_keys = []
@@ -196,7 +196,7 @@ def get_params(evaluator, func, var_args):
return result return result
def _unpack_var_args(evaluator, var_args, params): def _unpack_var_args(evaluator, var_args, func):
""" """
Yields a key/value pair, the key is None, if its not a named arg. Yields a key/value pair, the key is None, if its not a named arg.
""" """
@@ -218,7 +218,8 @@ def _unpack_var_args(evaluator, var_args, params):
# *args # *args
if expression_list[0] == '*': if expression_list[0] == '*':
arrays = evaluator.eval_expression_list(expression_list[1:]) arrays = evaluator.eval_expression_list(expression_list[1:])
iterators = [_iterate_star_args(a) for a in arrays] iterators = [_iterate_star_args(evaluator, a, expression_list[1:], func)
for a in arrays]
for values in list(zip_longest(*iterators)): for values in list(zip_longest(*iterators)):
argument_list.append((None, [v for v in values if v is not None])) argument_list.append((None, [v for v in values if v is not None]))
# **kwargs # **kwargs
@@ -227,7 +228,7 @@ def _unpack_var_args(evaluator, var_args, params):
for array in evaluator.eval_expression_list(expression_list[1:]): for array in evaluator.eval_expression_list(expression_list[1:]):
# Merge multiple kwargs dictionaries, if used with dynamic # Merge multiple kwargs dictionaries, if used with dynamic
# parameters. # parameters.
s = _star_star_dict(evaluator, array, expression_list[1:]) s = _star_star_dict(evaluator, array, expression_list[1:], func)
for name, (key, value) in s.items(): for name, (key, value) in s.items():
try: try:
dct[name][1].add(value) dct[name][1].add(value)
@@ -236,7 +237,7 @@ def _unpack_var_args(evaluator, var_args, params):
for key, values in dct.values(): for key, values in dct.values():
# merge **kwargs/*args also for dynamic parameters # merge **kwargs/*args also for dynamic parameters
for i, p in enumerate(params): for i, p in enumerate(func.params):
if str(p.get_name()) == str(key) and not p.stars: if str(p.get_name()) == str(key) and not p.stars:
try: try:
k, vs = argument_list[i] k, vs = argument_list[i]
@@ -264,19 +265,25 @@ def _unpack_var_args(evaluator, var_args, params):
return argument_list return argument_list
def _iterate_star_args(array): def _iterate_star_args(evaluator, array, expression_list, func):
from jedi.evaluate.representation import Instance
if isinstance(array, iterable.Array): if isinstance(array, iterable.Array):
for field_stmt in array: # yield from plz! for field_stmt in array: # yield from plz!
yield field_stmt yield field_stmt
elif isinstance(array, iterable.Generator): elif isinstance(array, iterable.Generator):
for field_stmt in array.iter_content(): for field_stmt in array.iter_content():
yield helpers.FakeStatement([field_stmt]) yield helpers.FakeStatement([field_stmt])
elif isinstance(array, Instance) and array.name == 'tuple':
pass
else: else:
# *args must be some sort of an array, otherwise -> ignore if expression_list:
pass # TODO need a warning here. m = "TypeError: %s() argument after * must be a sequence, not %s" \
% (func.name, array)
analysis.add(evaluator, 'type-error-star',
expression_list[0], message=m)
def _star_star_dict(evaluator, array, expression_list): def _star_star_dict(evaluator, array, expression_list, func):
dct = {} dct = {}
if isinstance(array, iterable.Array) and array.type == pr.Array.DICT: if isinstance(array, iterable.Array) and array.type == pr.Array.DICT:
for key_stmt, value_stmt in array.items(): for key_stmt, value_stmt in array.items():
@@ -294,9 +301,9 @@ def _star_star_dict(evaluator, array, expression_list):
dct[str(key)] = key, value_stmt dct[str(key)] = key, value_stmt
else: else:
if expression_list: if expression_list:
m = "TypeError: type object argument after ** must be a mapping, not %s" \ m = "TypeError: %s argument after ** must be a mapping, not %s" \
% (array) % (func.name, array)
analysis.add(evaluator, 'type-error-star-star-mapping', analysis.add(evaluator, 'type-error-star-star',
expression_list[0], message=m) expression_list[0], message=m)
return dct return dct

View File

@@ -100,5 +100,8 @@ mixed2(3, b=5)
# plain wrong arguments # plain wrong arguments
# ----------------- # -----------------
#! 12 type-error-star-star-mapping #! 12 type-error-star-star
simple(1, **[]) simple(1, **[])
#! 11 type-error-star
simple(1, *1)