-
-
Notifications
You must be signed in to change notification settings - Fork 1.9k
classmethod typing is weird #10396
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
Comments
I think you may have a typo in your message here — this is exactly the signature we currently have for |
Thanks Alex. I changed it to |
Yes, I think you're right about the The >>> @classmethod
... def bar(cls): return cls.X
...
>>> class Foo:
... X = 42
...
>>> bar.__get__(None, Foo)()
42
>>> bar.__get__(Foo(), None)()
42
>>> bar.__get__(Foo(), Foo)()
42
>>> bar.__get__('idk_whatever', Foo)()
42
>>> bar.__get__(None, None)()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: __get__(None, None) is invalid
>>> bar.__get__(Foo(), 'baz')()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 2, in bar
AttributeError: 'str' object has no attribute 'X' That implies the class classmethod(Generic[_T, _P, _R_co]):
def __init__(self, __f: Callable[Concatenate[type[_T], _P], _R_co]) -> None: ...
@overload
def __get__(self, __instance: object, __owner: type[T]) -> Callable[_P, _R_co]: ...
@overload
def __get__(self, __instance: _T, __owner: None = None) -> Callable[_P, _R_co]: ... Feel free to make a PR :) |
Makes sense. But shouldn't it be:
I feel like that's closer to the descriptor protocol. I know that it's probably possible to pass anything for |
Yes, you're right, the @overload
def __get__(self, __instance: _T | None, __owner: type[T]) -> Callable[_P, _R_co]: ...
@overload
def __get__(self, __instance: _T, __owner: None = None) -> Callable[_P, _R_co]: ... |
Thanks. Sorry I was a bit slower, but it was definitely on my todo list! |
It feels like the classmethod typing is slightly wrong.
Typeshed defines it as:
With mypy the following program fails:
The proper solution would probably be to type
__init__
as:Would such a pull request be accepted? If I change this in Mypy it fails with
error: Need type annotation for "x"
, which I think is much better (and Mypy could probably still infer the type variable_T
properly in the future). What do you think?The text was updated successfully, but these errors were encountered: