def bool_op_is_parenthesised(asttokens: ASTTokens, node: ast.BoolOp) -> bool: prev_token = asttokens.prev_token(_first_token(node)) next_token = asttokens.next_token(_last_token(node)) if prev_token.string == '(' and next_token.string == ')': return True return False
def wrap_function_def(asttokens: ASTTokens, node: ast.FunctionDef) -> WrappingSummary: positions = node_start_positions(asttokens, node.args.args) if node.args.vararg: # Account for the * before the name args_star = asttokens.prev_token(_first_token(node.args.vararg)) positions.append(Position(*args_star.start)) if node.args.kwonlyargs: # Account for the unnamed * if not node.args.vararg: comma = asttokens.prev_token(_first_token(node.args.kwonlyargs[0])) args_star = asttokens.prev_token(comma) positions.append(Position(*args_star.start)) positions += node_start_positions(asttokens, node.args.kwonlyargs) if node.args.kwarg: # Account for the ** before the name kwargs_stars = asttokens.prev_token(_first_token(node.args.kwarg)) positions.append(Position(*kwargs_stars.start)) summary = [(Position(pos.line, pos.col), MutationType.WRAP_INDENT) for pos in positions] close_paren = asttokens.next_token(_last_token(node.args)) args_end = Position(*close_paren.start) if not (node.args.kwonlyargs or node.args.kwarg): summary.append((args_end, MutationType.TRAILING_COMMA)) summary.append((args_end, MutationType.WRAP)) return summary
def wrap_class_def(asttokens: ASTTokens, node: ast.ClassDef) -> WrappingSummary: if not node.bases and not node.keywords: return [] named_args = node.keywords kwargs = None if named_args and named_args[-1].arg is None: named_args = node.keywords[:-1] kwargs = node.keywords[-1] args = [*node.bases, *named_args] summary = wrap_node_start_positions(asttokens, args) if kwargs is not None: kwargs_stars = asttokens.prev_token(_first_token(kwargs)) summary.append( (Position(*kwargs_stars.start), MutationType.WRAP_INDENT)) summary.append( (Position(*_last_token(kwargs).end), MutationType.TRAILING_COMMA)) summary.append((Position(*_last_token(kwargs).end), MutationType.WRAP)) else: last_token_before_body = asttokens.next_token(_last_token(args[-1])) summary.append(( Position(*last_token_before_body.start), MutationType.TRAILING_COMMA, )) summary.append(( Position(*last_token_before_body.start), MutationType.WRAP, )) return summary
def generator_is_parenthesised(asttokens: ASTTokens, node: ast.GeneratorExp) -> bool: prev_token = asttokens.prev_token(_first_token(node)) next_token = asttokens.next_token(_last_token(node)) if prev_token.string == '(' and next_token.string == ')': # These parens might be wrapping us prev_prev_token = asttokens.prev_token(prev_token) if prev_prev_token.string in ('(', ','): return True return False
def wrap_generator_exp(asttokens: ASTTokens, node: ast.GeneratorExp) -> WrappingSummary: summary = wrap_generator_body(asttokens, node.elt, node.generators) next_token = asttokens.next_token(_last_token(node)) if next_token.string == ')': summary.append(( Position(*next_token.start), MutationType.WRAP, )) return summary
def indent_interim_lines( asttokens: ASTTokens, wrapping_summary: WrappingSummary, ) -> WrappingSummary: if not wrapping_summary: # No changes to be made return wrapping_summary first_line = wrapping_summary[0][0].line last_line = wrapping_summary[-1][0].line if first_line == last_line: # Everything was on one line to start with, nothing for us to do. return wrapping_summary # Add indentations for things which were already wrapped somewhat. We don't # want to touch the first line (since that's the line we're splitting up), # but we do want to indent anything which was already on the last line we're # touching. for line in range(first_line + 1, last_line + 1): tok = asttokens.get_token(line, 0) if tok.start[0] != line: # We've got the last token on the previous line, but we want the # first on this line. tok = asttokens.next_token(tok, include_extra=True) assert tok.start[0] == line, "Token unexpectedly on wrong line" if tok.string == '\n': # Empty lines don't need indenting continue wrapping_summary.append((Position(*tok.start), MutationType.INDENT), ) wrapping_summary.sort(key=lambda x: x[0]) return wrapping_summary