-
-
Notifications
You must be signed in to change notification settings - Fork 276
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
false not-an-iterable for class method with @overload (2.5.7 regression) #1015
Comments
I can work around it by replacing |
@belm0 thanks for the report. |
Sure, happy to take this one |
This doesn't seem to have anything to do with class A:
def foo(self): ...
def foo(self):
yield
for _ in A().foo():
pass I think this has to do with the name resolution order, |
Ref pylint-dev#1015. When there are multiple statements defining some attribute ClassDef.igetattr filters out later definitions if they are not in the same scope as the first (to support cases like "self.a = 1; self.a = 2" or "self.items = []; self.items += 1"). However, it checks the scope of the first attribute against the *parent scope* of the later attributes. For mundane statements this makes no difference, but for scope-introducing statements such as FunctionDef these are not the same.
See workaround in pylint-dev/astroid#1015
pylint-dev/pylint#7624 have a use case related to this in pylint |
Getting a similar problem with from __future__ import annotations
from typing import Any, Union, overload
class device:
...
class Tensor:
...
class dtype:
...
class Module:
def __call__(self, *args: Any, **kwargs: Any) -> Any:
...
@overload
def to(self, dtype: Union[dtype, str]) -> Module:
...
@overload
def to(self, tensor: Tensor) -> Module:
...
def to(self, *args, **kwargs):
return self
tensor = Tensor()
module = Module()
_ = module(tensor) # OK
module = module.to("cpu")
_ = module(tensor) # a.py:46:4: E1102: module is not callable (not-callable)
|
Ref pylint-dev#1015. When there are multiple statements defining some attribute ClassDef.igetattr filters out later definitions if they are not in the same scope as the first (to support cases like "self.a = 1; self.a = 2" or "self.items = []; self.items += 1"). However, it checks the scope of the first attribute against the *parent scope* of the later attributes. For mundane statements this makes no difference, but for scope-introducing statements such as FunctionDef these are not the same.
…attr()` (#1173) Ref #1015. When there are multiple statements defining some attribute ClassDef.igetattr filters out later definitions if they are not in the same scope as the first (to support cases like "self.a = 1; self.a = 2" or "self.items = []; self.items += 1"). However, it checks the scope of the first attribute against the *parent scope* of the later attributes. For mundane statements this makes no difference, but for scope-introducing statements such as FunctionDef these are not the same. Fix this, and then filter to just last declared function (unless a property is involved). --------- Co-authored-by: Jacob Walls <jacobtylerwalls@gmail.com>
THANKS @jacobtylerwalls -- this was a major bug for pre-typing code that returned different things depending on settings (would not write new code for that today) and needed |
Steps to reproduce
Starting from astroid 2.5.7, I'm seeing false not-an-iterable when generator class methods are annotated with
@overload
.If
@overload
is removed, or the function is moved to the module level, or I switch to astroid 2.5.6, the problem goes away.It happens with pylint-2.8.3 or pylint-3.0.0a3.
Current behavior
E1133: Non-iterable value MyClass().transitions('hello') is used in an iterating context (not-an-iterable)
Expected behavior
no error
The text was updated successfully, but these errors were encountered: