def transform(self, node, results): if self.filename in blacklist: return elif self.filename == 'mercurial/util.py': touch_import('.', 'py3kcompat', node=node) formatstr = results['formatstr'].clone() data = results['data'].clone() formatstr.prefix = '' # remove spaces from start if isnumberremainder(formatstr, data): return # We have two possibilities: # 1- An identifier or name is passed, it is going to be a leaf, thus, we # just need to copy its value as an argument to the formatter; # 2- A tuple is explicitly passed. In this case, we're gonna explode it # to pass to the formatter # TODO: Check for normal strings. They don't need to be translated if is_tuple(data): args = [formatstr, Comma().clone()] + \ [c.clone() for c in data.children[:]] else: args = [formatstr, Comma().clone(), data] call = Call(Name('bytesformatter', prefix=' '), args) return call
def transform(self, node, results): syms = self.syms exc = results["exc"].clone() if exc.type == token.STRING: msg = "Python 3 does not support string exceptions" self.cannot_convert(node, msg) return # Python 2 supports # raise ((((E1, E2), E3), E4), E5), V # as a synonym for # raise E1, V # Since Python 3 will not support this, we recurse down any tuple # literals, always taking the first element. if is_tuple(exc): while is_tuple(exc): # exc.children[1:-1] is the unparenthesized tuple # exc.children[1].children[0] is the first element of the tuple exc = exc.children[1].children[0].clone() exc.prefix = u" " if "val" not in results: # One-argument raise new = pytree.Node(syms.raise_stmt, [Name(u"raise"), exc]) new.prefix = node.prefix return new val = results["val"].clone() if is_tuple(val): args = [c.clone() for c in val.children[1:-1]] else: val.prefix = u"" args = [val] return pytree.Node(syms.raise_stmt, [Name(u"raise"), Call(exc, args)], prefix=node.prefix)
def is_tuple(self, string): return fixer_util.is_tuple(parse(string, strip_levels=2))
def transform(self, node, results): syms = self.syms exc = results["exc"].clone() if exc.type == token.STRING: msg = "Python 3 does not support string exceptions" self.cannot_convert(node, msg) return # Python 2 supports # raise ((((E1, E2), E3), E4), E5), V # as a synonym for # raise E1, V # Since Python 3 will not support this, we recurse down any tuple # literals, always taking the first element. if is_tuple(exc): while is_tuple(exc): # exc.children[1:-1] is the unparenthesized tuple # exc.children[1].children[0] is the first element of the tuple exc = exc.children[1].children[0].clone() exc.prefix = u" " if "tb" in results: tb = results["tb"].clone() else: tb = None if "val" in results: val = results["val"].clone() if is_tuple(val): # Assume that exc is a subclass of Exception and call exc(*val). args = [c.clone() for c in val.children[1:-1]] exc = Call(exc, args) elif val.type in (token.NUMBER, token.STRING): # Handle numeric and string literals specially, e.g. # "raise Exception, 5" -> "raise Exception(5)". val.prefix = u"" exc = Call(exc, [val]) elif val.type == token.NAME and val.value == u"None": # Handle None specially, e.g. # "raise Exception, None" -> "raise Exception". pass else: # val is some other expression. If val evaluates to an instance # of exc, it should just be raised. If val evaluates to None, # a default instance of exc should be raised (as above). If val # evaluates to a tuple, exc(*val) should be called (as # above). Otherwise, exc(val) should be called. We can only # tell what to do at runtime, so defer to future.utils.raise_(), # which handles all of these cases. touch_import_top(u"future.utils", u"raise_", node) exc.prefix = u"" args = [exc, Comma(), val] if tb is not None: args += [Comma(), tb] return Call(Name(u"raise_"), args) if tb is not None: tb.prefix = "" exc_list = Attr(exc, Name('with_traceback')) + [ArgList([tb])] else: exc_list = [exc] return pytree.Node(syms.raise_stmt, [Name(u"raise")] + exc_list, prefix=node.prefix)
def _create_logging_call(self, log_call_args, node): try: len_log_call_args = len(log_call_args) if (len_log_call_args == 1 and log_call_args[0].type == syms.atom and log_call_args[0].children[0].type == token.LPAR and log_call_args[0].children[2].type == token.RPAR): candidate = log_call_args[0].children[1] log_call_args = candidate.children if \ candidate.type == syms.testlist_gexp else [candidate] len_log_call_args = len(log_call_args) string_args = self._literal_string_args(log_call_args) len_log_call_args = len(log_call_args) if not string_args and len_log_call_args > 1: log_call_args.extend( [Leaf(token.COMMA, ','), Leaf(token.STRING, "''")]) string_args = self._literal_string_args(log_call_args) if string_args: aggregation_string_args = deque() index, leaf = string_args[0] if leaf.type == syms.term: string_args = leaf.children[2] if is_tuple(string_args): _string_args = [ c for c in string_args.children[1].children ] aggregation_string_args.extend( [Leaf(token.COMMA, ',')] + _string_args) else: aggregation_string_args.extend( [Leaf(token.COMMA, ','), string_args]) leaf = leaf.children[0] lead, aggregation_string, trail = _get_string_contents( leaf.value) aggregation_string = _thingy(aggregation_string, aggregation_string_args, log_call_args[index + 1:]) aggregation_string = _thingy(aggregation_string, aggregation_string_args, log_call_args[:index], prepend=True) if (len(aggregation_string_args) > 2 and token.COMMA == aggregation_string_args[-1].type): aggregation_string_args.pop() for arg in aggregation_string_args: arg.prefix = ' ' if arg.type != token.COMMA else '' log_call_args = [ String(''.join([lead, aggregation_string, trail])) ] + [a.clone() for a in aggregation_string_args] new_node = Call(Name(u"%s.info" % LOGGER_NAME), [a.clone() for a in log_call_args], prefix=node.prefix) touch_import(None, 'logging', node) add_global_assignment_after_imports(LOGGER_NAME, LOGGER_GET.clone(), node) except Exception: logger.exception('Node is:%s', node) raise return new_node