Overloaded class methods not supported by Protocol
Nobody has claimed this yet.
- Dominant language
- Python
- Stars
- 20.6k
- Forks
- 3.3k
- PR merge metrics
- PR metrics pending
Description
Bug Report
If a Protocol contains a class method, a class (or an object of this class) won't fulfill the Protocol if the class method is overloaded.
To Reproduce
from typing import Protocol, overload
class SupportsFooOnClass(Protocol):
@classmethod
def foo(cls, x: int) -> str: ...
class Fooer:
@overload
@classmethod
def foo(cls, x: int) -> str:
...
@overload
@classmethod
def foo(cls, x: float) -> complex:
...
@classmethod
def foo(cls, x: int | float) -> str | complex:
if isinstance(x, int):
return "foo"
return 5j
def use_foo(fooable: SupportsFooOnClass):
pass
use_foo(Fooer())
use_foo(Fooer)
https://mypy-play.net/?mypy=latest&python=3.10&gist=eb4e527b43fb5b249b7afeadd5aa853d
Expected Behavior
Success.
Class Fooer supports a class method foo with one argument of type int and return type of str.
The same code passes pyright's check.
Actual Behavior
main.py:31: error: Argument 1 to "use_foo" has incompatible type "Fooer"; expected "SupportsFooOnClass" [arg-type]
main.py:31: note: Protocol member SupportsFooOnClass.foo expected class or static method
main.py:32: error: Argument 1 to "use_foo" has incompatible type "type[Fooer]"; expected "SupportsFooOnClass" [arg-type]
main.py:32: note: Protocol member SupportsFooOnClass.foo expected class or static method
Found 2 errors in 1 file (checked 1 source file)
Your Environment
- Mypy version used: 1.7.1
- Mypy command-line flags: -
- Mypy configuration options from
mypy.ini(and other config files): - - Python version used: 3.10
Contributor guide
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Research direction
Start by running the minimal Python reproduction from the issue and compare mypy's handling of the Protocol, overloaded class method, and direct class or instance calls. Trace the Protocol compatibility check and overload handling, then verify that both use_foo(Fooer()) and use_foo(Fooer) pass without errors while preserving the existing overload behavior.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- python
- Domain
- tooling
- Issue type
- Bug
- Difficulty
- 4/5
- Estimated time
- 3-5 days
- Activity status
- Quiet
- Clarity
- Mostly clear
- Newbie friendliness
- 45/100