Closed aholmes closed 1 month ago
Please refer to this documentation for details about how pyright interprets class and instance variables.
If you want x
to be treated as a "pure" instance variable — one that cannot have a class variable backing it, then you should declare the variable in the __init__
method or some other instance method.
class Foo:
def func(self):
self.x: int
Foo.x # Error
Is your feature request related to a problem? Please describe. This is related to #6938 and is a requested improvement for this specific issue #3886.
With this code
Foo().x
raises anAttributeError
:Foo.x
raises and `AttributeError:Describe the solution you’d like
As has already been referenced, PEP526 states:
My request is two-part:
I interpret the intent of this to mean any accesses of a class member is an error regardless of Python code's ability to set
Foo.x
through other means. So the first part of my request is thatFoo.x
should be flagged, and the member should not show up in any "intellisense" (I think this last part is pylance, though). I believe this position is bolstered by the existence ofClassVar[T]
, which is intended to indicate that a class member is in fact a class member. This implies that any "class member"-looking declarations not declared withClassVar[T]
are in fact instance members. To me, this means the by-design concerns mentioned in #3886 can be "short-circuited" by avoiding what is possible in Python and instead taking the stance that what is declared is what is intended and correct, and limiting Pyright's "responsibility" to what it can determine about this class and its usage.Here's an example:
Nothing in this code's declaration indicates that
Foo.x
is valid, but Pyright does not indicate the possibility of an issue.Similarly, Pyright does not error with
self.x
, but callingFoo().func()
is a runtime error:@erictraut mentioned this:
This does indeed catch if the instance member is not assigned, but it does not affect the class member access that causes a runtime error.
The second part of my request regards usage of
ClassVar
:I wonder if there is some kind of flagging that can be done here despite Python's ability to set
x
from anywhere. Having the ability to flag this as a warning could go a long way toward catching possible errors, and gives developers the opportunity to ignore a flag when they know it's not an error.I understand implementing this request is complex due to how Python works, and the likelihood of causing problems in existing codebases. I am hoping there is some form of limited type checking that can occur in these cases so that developers might have the option to decide for themselves how to handle flagging of these issues in their code.
For your reference, here is my Pyright configuration.