-
Notifications
You must be signed in to change notification settings - Fork 216
Closed
astral-sh/ruff
#18466Labels
Description
Summary
Consider the following snippet:
def b() -> bool:
return False
class Foo:
if b():
x: int = 42
def f(y: Foo):
if hasattr(y, "x"):
reveal_type(y) # revealed: Foo
print(y.x) # error[possibly-unbound-attribute]: Attribute `x` on type `Foo` is possibly unboundIn the hasattr() branch, we narrow the type of y to Foo & <protocol with members 'x'>, but then immediately simplify that intersection to Foo, since we know that all Foo members have an x member. But this simplification is incorrect, because it causes us to then emit a false positive when attempting to access the x member: we report the attribute as possibly unbound, even though the user just checked that it isn't!
We should only simplify these synthesized-protocol intersections if another element in the intersection has a definitely bound attribute of the relevant name.
Reactions are currently unavailable