agronholm / typeguard

Run-time type checker for Python
Other
1.55k stars 114 forks source link

Return value (method) is not compatible with the P protocol because it has no attribute named '__weakref__' #483

Closed jolaf closed 2 months ago

jolaf commented 2 months ago

Things to check first

Typeguard version

4.3.0

Python version

3.12.3

What happened?

Traceback (most recent call last):
  File "/.../test.py", line 3, in <module>
    import A
  File "<frozen importlib._bootstrap>", line 1360, in _find_and_load
  File "<frozen importlib._bootstrap>", line 1331, in _find_and_load_unlocked
  File "<frozen importlib._bootstrap>", line 935, in _load_unlocked
  File "/home/.../.local/lib/python3.12/site-packages/typeguard/_importhook.py", line 98, in exec_module
    super().exec_module(module)
  File "/.../A.py", line 13, in <module>
    print(A().g()())
          ^^^^^^^
  File "/.../A.py", line 11, in g
    return self.f
  File "/home/.../.local/lib/python3.12/site-packages/typeguard/_functions.py", line 165, in check_return_type
    check_type_internal(retval, annotation, memo)
  File "/home/.../.local/lib/python3.12/site-packages/typeguard/_checkers.py", line 861, in check_type_internal
    checker(value, origin_type, args, memo)
  File "/home/.../.local/lib/python3.12/site-packages/typeguard/_checkers.py", line 738, in check_protocol
    raise TypeCheckError(
typeguard.TypeCheckError: the return value (method) is not compatible with the P protocol because it has no attribute named '__weakref__'

How can we reproduce the bug?

test.py:

from typeguard import install_import_hook
with install_import_hook(('A',)):
    import A

A.py:

from typing import Protocol

class P(Protocol):
    def __call__(self) -> str: ...

class A:
    def f(self) -> str:
        return "OK"

    def g(self) -> P:
        return self.f

print(A().g()())
$ python3 A.py
OK

$ python3 test.py
<crash>
agronholm commented 2 months ago

Duplicate of #479.