Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion rewrite-python/rewrite/src/rewrite/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

# helps pytest to rewrite the assert statements in test.py
try:
import pytest # ty: ignore[unresolved-import]
import pytest
pytest.register_assert_rewrite("rewrite.test")
except ImportError:
pass # pytest not available, skip assert rewriting
Expand Down
6 changes: 3 additions & 3 deletions rewrite-python/rewrite/src/rewrite/java/extensions.py
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ def visit_container(v: 'JavaVisitor', container: Optional[JContainer[J2]], p: P)
v.cursor = Cursor(v.cursor, container)
before = v.visit_space(container.before, p)
js = list_map(lambda el: v.visit_right_padded(el, p), container.padding.elements)
v.cursor = v.cursor.parent # ty: ignore[invalid-assignment] # cursor.parent is Optional[Cursor]; ty#1379
v.cursor = v.cursor.parent # ty: ignore[invalid-assignment] # cursor.parent is Optional[Cursor] (ty#628)

return container if js is container.padding.elements and before is container.before else JContainer(before, js, container.markers)

Expand All @@ -30,7 +30,7 @@ def visit_right_padded(v: 'JavaVisitor', right: Optional[JRightPadded[T]], p: P)
v.cursor = Cursor(v.cursor, right)
if isinstance(t, Tree):
t = v.visit_and_cast(t, T, p)
v.cursor = v.cursor.parent # ty: ignore[invalid-assignment] # cursor.parent is Optional[Cursor]; ty#1379
v.cursor = v.cursor.parent # ty: ignore[invalid-assignment] # cursor.parent is Optional[Cursor] (ty#628)

if t is None:
return None
Expand All @@ -50,7 +50,7 @@ def visit_left_padded(v: 'JavaVisitor', left: Optional[JLeftPadded[T]], p: P) ->
t = left.element
if isinstance(t, Tree):
t = v.visit_and_cast(t, T, p)
v.cursor = v.cursor.parent # ty: ignore[invalid-assignment] # cursor.parent is Optional[Cursor]; ty#1379
v.cursor = v.cursor.parent # ty: ignore[invalid-assignment] # cursor.parent is Optional[Cursor] (ty#628)

if left.element is t and before is left.before:
return left
Expand Down
2 changes: 1 addition & 1 deletion rewrite-python/rewrite/src/rewrite/java/support_types.py
Original file line number Diff line number Diff line change
Expand Up @@ -589,5 +589,5 @@ def build_nullable(cls, before: Optional[JContainer[J2]], elements: Optional[Lis
def empty(cls) -> JContainer[J2]:
if cls._EMPTY is None:
cls._EMPTY = JContainer(Space.EMPTY, [], Markers.EMPTY)
return cls._EMPTY # type: ignore[return-value] # _EMPTY is JContainer[J] but J2 is bound to J
return cls._EMPTY # ty: ignore[invalid-return-type] # _EMPTY is JContainer[J] but J2 is bound to J

3 changes: 3 additions & 0 deletions rewrite-python/rewrite/src/rewrite/java/support_types.pyi
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ from rewrite.utils import replace_if_changed
class J(Tree):
@property
def prefix(self) -> Space: ...
def replace(self, **kwargs: Any) -> Self: ...
def is_acceptable(self, v: TreeVisitor[Any, P], p: P) -> bool: ...
def accept(self, v: TreeVisitor[Any, P], p: P) -> Optional[Any]: ...
def accept_java(self, v: 'JavaVisitor[P]', p: P) -> Optional['J']: ...
Expand Down Expand Up @@ -116,12 +117,14 @@ class JavaType(ABC):
@property
def bounds(self) -> List[JavaType]: ...

@dataclass
class Union:
_bounds: Optional[List[JavaType]]

@property
def bounds(self) -> List[JavaType]: ...

@dataclass
class Intersection:
_bounds: Optional[List[JavaType]]

Expand Down
2 changes: 1 addition & 1 deletion rewrite-python/rewrite/src/rewrite/parser.py
Original file line number Diff line number Diff line change
Expand Up @@ -141,7 +141,7 @@ def with_erroneous(self, erroneous: Optional[SourceFile]) -> 'ParseError':
return self if erroneous is self._erroneous else replace(self, _erroneous=erroneous)

def printer(self, cursor: Cursor) -> TreeVisitor[Tree, PrintOutputCapture[P]]:
return PrinterFactory.current().create_printer(cursor) # ty: ignore[unresolved-attribute] # PrinterFactory.current() is always set
return PrinterFactory.current().create_printer(cursor) # ty: ignore[unresolved-attribute] # guarded: PrinterFactory.current() always set here

def is_acceptable(self, v: TreeVisitor[Any, P], p: P) -> bool:
return v.is_adaptable_to(ParseErrorVisitor)
Expand Down
16 changes: 8 additions & 8 deletions rewrite-python/rewrite/src/rewrite/python/_parser_visitor.py
Original file line number Diff line number Diff line change
Expand Up @@ -774,7 +774,7 @@ def visit_Import(self, node):
prefix = self.__source_before('import')
imp = self.__convert(node.names[0])
assert imp is not None
return imp.replace(prefix=prefix, qualid=imp.qualid.replace(prefix=imp.prefix))
return imp.replace(prefix=prefix, qualid=imp.qualid.replace(prefix=imp.prefix)) # ty: ignore[unresolved-attribute] # imp is Import at runtime

prefix = self.__source_before('import')
names_prefix = self.__whitespace()
Expand Down Expand Up @@ -1197,7 +1197,7 @@ def __convert_match_pattern(self, node):
py.MatchCase.Pattern.Kind.GROUP,
JContainer(
prefix,
[JRightPadded(inner.replace(prefix=inner_prefix) if hasattr(inner, 'replace') else inner, Space.EMPTY, Markers.EMPTY)], # ty: ignore[call-non-callable]
[JRightPadded(inner.replace(prefix=inner_prefix) if hasattr(inner, 'replace') else inner, Space.EMPTY, Markers.EMPTY)],
Markers.EMPTY
),
None
Expand Down Expand Up @@ -2243,7 +2243,7 @@ def __map_decorator(self, decorator) -> j.Annotation:
name = name.replace(prefix=extra_parens[-1][1]) # ty: ignore[unresolved-attribute] # recursive call returns unknown

# Wrap in extra parentheses (innermost to outermost)
wrapped: Expression = name
wrapped: Expression = name # ty: ignore[invalid-assignment]
for i in range(len(extra_parens) - 1, -1, -1):
paren_prefix, _ = extra_parens[i]
suffix = self.__whitespace()
Expand Down Expand Up @@ -2769,7 +2769,7 @@ def __convert_type(self, node) -> Optional[TypeTree]:
prefix = self.__whitespace()
converted_type = self.__convert_internal(node, self.__convert_type, self.__convert_type_mapper)
if isinstance(converted_type, TypeTree):
return converted_type.replace(prefix=prefix) # ty: ignore[unresolved-attribute] # TypeTree base class doesn't have replace
return converted_type.replace(prefix=prefix) # TypeTree base class doesn't have replace
else:
return py.ExpressionTypeTree(
random_id(),
Expand Down Expand Up @@ -3065,14 +3065,14 @@ def ident_or_field(parts: List[str]) -> NameTree:
return ident_or_field(name.split('.'))

def __convert_all(self, trees: Sequence) -> List[J2]:
return [c for tree in trees if (c := self.__convert(tree)) is not None] # ty: ignore[invalid-return-type]
return [c for tree in trees if (c := self.__convert(tree)) is not None] # ty: ignore[invalid-return-type] # J list, J2 is bound to J

def __convert_block(self, statements: Sequence[Statement], delim: str = ':') -> j.Block:
prefix = self.__source_before(delim)
if statements:
statements = [self.__pad_statement(cast(ast.stmt, s)) for s in statements] # ty: ignore[invalid-assignment]
statements = [self.__pad_statement(cast(ast.stmt, s)) for s in statements] # ty: ignore[invalid-assignment] # padded statement list type
else:
statements = [self.__pad_right(j.Empty(random_id(), Space.EMPTY, Markers.EMPTY), Space.EMPTY)] # ty: ignore[invalid-assignment]
statements = [self.__pad_right(j.Empty(random_id(), Space.EMPTY, Markers.EMPTY), Space.EMPTY)] # ty: ignore[invalid-assignment] # padded statement list type
return j.Block(
random_id(),
prefix,
Expand All @@ -3095,7 +3095,7 @@ def __pad_statement(self, stmt: ast.stmt) -> JRightPadded[Statement]:
self._token_idx = save_idx
padding = Space.EMPTY
markers = Markers.EMPTY
return JRightPadded(statement, padding, markers) # ty: ignore[invalid-return-type] # statement is J|None from __convert_statement
return JRightPadded(statement, padding, markers) # ty: ignore[invalid-return-type] # statement is J from __convert_statement

def __pad_list_element(self, element: J2, last: bool = False, pad_last: bool = True, delim: str = ',',
end_delim: Optional[str] = None) -> JRightPadded[J2]:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -172,7 +172,7 @@ def _convert_leaf(self, leaf: parso_tree.PythonLeaf) -> Optional[j.J]:
prefix = self._parse_space(leaf.prefix)

# parso 0.7.x uses lowercase type names (e.g. 'name', 'number')
leaf_type = leaf.type.upper()
leaf_type = leaf.type.upper() # ty: ignore[unresolved-attribute] # parso leaf.type is always str

if leaf_type == 'NAME' or leaf_type == 'KEYWORD':
return j.Identifier(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ def visit_compilation_unit(self, cu: CompilationUnit, p: P) -> J:
return super().visit_compilation_unit(cu, p)

def visit_statement(self, stmt: Statement, p: P) -> J:
stmt = super().visit_statement(stmt, p)
stmt = super().visit_statement(stmt, p) # ty: ignore[invalid-assignment] # visitor covariance

parent_cursor = self.cursor.parent_tree_cursor()
top_level = isinstance(parent_cursor.value, CompilationUnit)
Expand All @@ -41,7 +41,7 @@ def visit_statement(self, stmt: Statement, p: P) -> J:
else:
min_lines = max(self._style.minimum.around_top_level_classes_functions if isinstance(stmt, (ClassDeclaration, MethodDeclaration)) else 0,
self._style.minimum.after_top_level_imports if prev_import else 0)
stmt = _adjusted_lines_for_tree(stmt, min_lines, self._style.keep_maximum.in_declarations)
stmt = _adjusted_lines_for_tree(stmt, min_lines, self._style.keep_maximum.in_declarations) # ty: ignore[invalid-assignment] # visitor covariance
else:
in_block = isinstance(parent_cursor.value, Block)
in_class = in_block and isinstance(parent_cursor.parent_tree_cursor().value, ClassDeclaration)
Expand All @@ -63,7 +63,7 @@ def visit_statement(self, stmt: Statement, p: P) -> J:
if prev_import:
min_lines = max(min_lines, self._style.minimum.after_local_imports)

stmt = _adjusted_lines_for_tree(stmt, min_lines, max_lines)
stmt = _adjusted_lines_for_tree(stmt, min_lines, max_lines) # ty: ignore[invalid-assignment] # visitor covariance
return stmt

def post_visit(self, tree: T, p: P) -> Optional[T]:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,9 +26,9 @@ def post_visit(self, tree: T, p: P) -> Optional[T]:
if not previous_statement or not previous_statement.markers.find_first(Semicolon):
new_prefix = tree.prefix.replace(whitespace='\n' + tree.prefix.whitespace)
if isinstance(tree, ExpressionStatement):
tree = tree.replace(expression=tree.expression.replace(prefix=new_prefix))
tree = tree.replace(expression=tree.expression.replace(prefix=new_prefix)) # ty: ignore[invalid-assignment]
else:
tree = tree.replace(prefix=new_prefix)
tree = tree.replace(prefix=new_prefix) # ty: ignore[invalid-assignment]

return tree

Expand Down Expand Up @@ -67,4 +67,4 @@ def modify_comment(c: PyComment) -> PyComment:
if comments:
new_prefix = new_prefix.replace(comments=comments)

return j.replace(prefix=new_prefix)
return j.replace(prefix=new_prefix) # ty: ignore[invalid-return-type]
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ def __init__(self, style: GeneralFormatStyle, stop_after: Optional[Tree] = None)

def visit_space(self, space: Optional[Space], p: P) -> Space:
if not space or space is Space.EMPTY or not space.whitespace:
return space # type: ignore
return space # ty: ignore[invalid-return-type]
s = space.replace(whitespace=_normalize_new_lines(space.whitespace, self._style.use_crlf_new_lines))

def process_comment(comment: Comment) -> Comment:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ def visit_class_declaration(self, class_decl: ClassDeclaration, p: P) -> J:
implements=space_before_container(c.padding.implements, self._style.before_parentheses.method_call)
)

param_size = len(c.padding.implements.elements)
param_size = len(c.padding.implements.elements) # ty: ignore[unresolved-attribute] # guarded by truthiness check above
use_space = self._style.within.method_call_parentheses

def _process_argument(index, arg, args_size):
Expand All @@ -46,9 +46,9 @@ def _process_argument(index, arg, args_size):

if c.implements:
c = c.padding.replace(
implements=c.padding.implements.padding.replace(
implements=c.padding.implements.padding.replace( # ty: ignore[unresolved-attribute] # guarded by truthiness check above
elements=list_map(lambda arg, index: _process_argument(index, arg, param_size),
c.padding.implements.padding.elements)))
c.padding.implements.padding.elements))) # ty: ignore[unresolved-attribute] # guarded by truthiness check above
return c

def visit_method_declaration(self, method: MethodDeclaration, p: P) -> J:
Expand Down Expand Up @@ -350,12 +350,12 @@ def _process_element(index, arg, last, use_space):
return arg

pt = pt.padding.replace(
type_parameters=pt.padding.type_parameters.padding.replace(
type_parameters=pt.padding.type_parameters.padding.replace( # ty: ignore[unresolved-attribute] # guarded by truthiness check above
elements=list_map(
lambda arg, idx: _process_element(idx, arg,
last=idx == len(pt.padding.type_parameters.padding.elements) - 1,
last=idx == len(pt.padding.type_parameters.padding.elements) - 1, # ty: ignore[unresolved-attribute] # guarded by truthiness check above
use_space=self._style.within.brackets),
pt.padding.type_parameters.padding.elements
pt.padding.type_parameters.padding.elements # ty: ignore[unresolved-attribute] # guarded by truthiness check above
)
)
)
Expand Down Expand Up @@ -526,9 +526,9 @@ def space_before(j: J2, add_space: bool) -> J2:
return j

if add_space and not_single_space(prefix.whitespace):
return j.replace(prefix=prefix.replace(whitespace=" ")) # ty: ignore[unresolved-attribute]
return j.replace(prefix=prefix.replace(whitespace=" "))
elif not add_space and only_spaces_and_not_empty(prefix.whitespace):
return j.replace(prefix=prefix.replace(whitespace="")) # ty: ignore[unresolved-attribute]
return j.replace(prefix=prefix.replace(whitespace=""))

return j

Expand Down Expand Up @@ -580,7 +580,7 @@ def space_before_left_padded(j: JLeftPadded[J2], add_space) -> JLeftPadded[J2]:


def space_after(j: J2, add_space: bool) -> J2:
space: Space = cast(Space, j.after)
space: Space = cast(Space, j.after) # ty: ignore[unresolved-attribute] # J2 is JRightPadded at call site
if space.comments or '\\' in space.whitespace:
return j

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -101,7 +101,7 @@ def post_visit(self, tree: T, p: P) -> Optional[T]:

def visit_space(self, space: Optional[Space], p: P) -> Space:
if space is None:
return space # type: ignore
return space # ty: ignore[invalid-return-type]

space_context = self.cursor.get_nearest_message("space_context")
parent = self.cursor.parent
Expand Down Expand Up @@ -262,7 +262,7 @@ def visit_right_padded(self, right: Optional[JRightPadded], p: P) -> Optional[JR
else:
after = self.visit_space(right.after, p)

self.cursor = self.cursor.parent # type: ignore
self.cursor = self.cursor.parent # ty: ignore[invalid-assignment] # cursor property setter (ty#628)
if t is right.element and after is right.after:
return right
return right.replace(element=t, after=after)
Expand Down Expand Up @@ -315,7 +315,7 @@ def visit_container(self, container: Optional[JContainer], p: P) -> Optional[JCo
before = self.visit_space(container.before, p)
js = list_map(lambda t: self.visit_right_padded(t, p), container.padding.elements)

self._cursor = self._cursor.parent # type: ignore
self._cursor = self._cursor.parent # ty: ignore[invalid-assignment] # _cursor.parent is Optional[Cursor]

if container.padding.elements is js and container.before is before:
return container
Expand Down Expand Up @@ -576,7 +576,7 @@ def _check(tree, p):
p.found = True
return tree
return orig_visit(tree, p) if not p.found else tree
self._delegate.visit = _check
self._delegate.visit = _check # ty: ignore[invalid-assignment] # monkey-patching delegate visitor

def visit(self, tree, p, parent=None):
if p.found or tree is target:
Expand Down Expand Up @@ -637,7 +637,7 @@ def _check(tree, p):
p.found = True
return tree
return orig_visit(tree, p) if not p.found else tree
self._delegate.visit = _check
self._delegate.visit = _check # ty: ignore[invalid-assignment] # monkey-patching delegate visitor

def visit(self, tree, p, parent=None):
if p.found or tree is select:
Expand Down Expand Up @@ -699,7 +699,7 @@ def _visit_method_invocation_argument_j_type(self, elem: J, right: JRightPadded,
if "\n" not in body.prefix.last_whitespace:
self.cursor.parent_or_throw.put_message("last_indent", indent + self._style.continuation_indent)

elem = self.visit_and_cast(elem, J, p)
elem = self.visit_and_cast(elem, J, p) # ty: ignore[invalid-assignment] # visit_and_cast returns Optional[J]
assert elem is not None
after = self._indent_to(right.after, indent)
if after.comments or "\n" in after.last_whitespace:
Expand Down
2 changes: 1 addition & 1 deletion rewrite-python/rewrite/src/rewrite/python/printer.py
Original file line number Diff line number Diff line change
Expand Up @@ -1202,7 +1202,7 @@ def visit_assignment(self, assignment: 'j.Assignment', p: PrintOutputCapture) ->
isinstance(parent_value, py.ExpressionStatement) or # J.Assignment is both Expression and Statement, so the wrapping ExpressionStatement is redundant here, but template-generated replacements can produce this nesting
(isinstance(parent_value, j.If) and parent_value.then_part == assignment) or
(isinstance(parent_value, j.If.Else) and parent_value.body == assignment) or
(isinstance(parent_value, Loop) and parent_value.body == assignment) # ty: ignore[unresolved-attribute] # Loop base class doesn't have body
(isinstance(parent_value, Loop) and parent_value.body == assignment) # ty: ignore[unresolved-attribute] # Loop subclasses have body
)

symbol = "=" if is_regular_assignment else ":="
Expand Down
Loading