Skip to content
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

mypy reports an error with a function with generic argument. #18544

Closed
s17b2-voroneckij opened this issue Jan 27, 2025 · 4 comments
Closed

mypy reports an error with a function with generic argument. #18544

s17b2-voroneckij opened this issue Jan 27, 2025 · 4 comments
Labels
bug mypy got something wrong

Comments

@s17b2-voroneckij
Copy link

Bug Report

For a function that accepts objects of A | B | C type, mypy is not correctly inferring types for function calls from that object.

To Reproduce
https://mypy-play.net/?mypy=latest&python=3.12&gist=a090296a66d822acabcb0e92e53f5871

from typing import Self, reveal_type, Protocol


class A:
    def dup(self) -> list[Self]:
        return [self, self]


class B:
    def dup(self) -> list[Self]:
        return [self, self]


class C:
    def dup(self) -> list[Self]:
        return [self, self]


class HasDup(Protocol):
    def dup(self) -> list[Self]: ...


def process[T: A | B | C](elem: T) -> list[T]:
    reveal_type(elem.dup)
    duplicated: list[T] = elem.dup()
    return duplicated


process(A())
process(B())
process(C())

Expected Behavior
No error to be reported

Actual Behavior
main.py:24: note: Revealed type is "Union[def () -> builtins.list[main.A], def () -> builtins.list[main.B], def () -> builtins.list[main.C]]"
main.py:25: error: Incompatible types in assignment (expression has type "list[A] | list[B] | list[C]", variable has type "list[T]") [assignment]
Found 1 error in 1 file (checked 1 source file)

Your Environment

  • Mypy version used: 1.14.1
  • Mypy command-line flags: none
  • Mypy configuration options from mypy.ini (and other config files): none
  • Python version used: 3,12
@s17b2-voroneckij s17b2-voroneckij added the bug mypy got something wrong label Jan 27, 2025
@A5rocks
Copy link
Collaborator

A5rocks commented Jan 28, 2025

Note that list[A | B | C] is not list[A] | list[B] | list[C] because list is an invariant type. Here's some ideas for what you could do:

@A5rocks A5rocks closed this as not planned Won't fix, can't repro, duplicate, stale Jan 28, 2025
@s17b2-voroneckij
Copy link
Author

@A5rocks, using Sequence doesn`t help in any way:
https://mypy-play.net/?mypy=latest&python=3.12&gist=8592bae5e6db2338470bf68cf73cfbcf

The issue I think is that mypy incorrectly detects the type of elem.dup. It should be () -> Sequence[T] and not Union[def () -> typing.Sequence[main.A], def () -> typing.Sequence[main.B], def () -> typing.Sequence[main.C]]

@A5rocks
Copy link
Collaborator

A5rocks commented Jan 28, 2025

Good catch. I searched a bit and I think that's #18170 #16826.

My second recommendation should hopefully work though.

@s17b2-voroneckij
Copy link
Author

@A5rocks , yes, the second one works indeed

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug mypy got something wrong
Projects
None yet
Development

No branches or pull requests

2 participants