Type narrowing of `target: type[T]` using insinstance seems to fool mypy
Dieses Issue hat noch niemand übernommen.
- Vorherrschende Sprache
- Python
- Sterne
- 20.6k
- Forks
- 3.3k
- PR-Merge-Kennzahlen
- PR-Kennzahlen ausstehend
Beschreibung
Bug Report
Well, I was writing some sort of converter from unstructured data to a dataclass, so I had a function that uses f[T](obj, target_type: type[T]) -> T and while in the end I stick to typing.cast for that, I also tried several solutions, they are below.
One of them intuitively should(?) work (return_checktype), but mypy refuses to follow them, and one of them is obviously wrong in hindsight (return_checkval), but mypy is happy with it.
To Reproduce
from typing import reveal_type
def return_checkval[T](target_type: type[T]) -> T:
# runtime check that target_type is int
if isinstance(target_type, int):
reveal_type(target_type)
return 42 # and they lived happily ever after
raise ValueError("Unsupported type")
x = return_checkval(int)
print(x)
def return_checktype[T](target_type: type[T]) -> T:
# runtime check that target_type is int
if target_type is int:
reveal_type(target_type)
return 42 # errors here
raise ValueError("Unsupported type")
# example test
x = return_checktype(int)
print(x)
Expected Behavior
At the very least, it should have two reveal_type outputs, and it should reject the first function completely. That's what (based)pyright.
Ideally, it should also allow the second function, but (based)pyright also rejects it :(
Actual Behavior
t.py:20: note: Revealed type is "type[T`-1]"
t.py:21: error: Incompatible return value type (got "int", expected "T") [return-value]
Found 1 error in 1 file (checked 1 source file)
Traceback (most recent call last):
File "/private/tmp/test/t.py", line 13, in <module>
x = return_checkval(int)
File "/private/tmp/test/t.py", line 10, in return_checkval
raise ValueError("Unsupported type")
ValueError: Unsupported type
Your Environment
mypy version 1.19.1 (compiled yes)
python version .. honestly have no idea which one it uses, but python --version is 3.14
just run it mypy . from the folder in /tmp
Beitragsleitfaden
Erste Schritte
- Lies das ganze Issue und danach den Beitragsleitfaden des Projekts.
- Schreib ins Issue, dass du es übernimmst — das erspart doppelte Arbeit.
- Forke das Repository und arbeite in einem Branch.
- Öffne einen Pull Request, der die Issue-Nummer nennt.
Rechercherichtung
Beginne damit, den bereitgestellten Reproducer mit mypy 1.19.1 auszuführen, und vergleiche die von ihm angezeigten Typen und Diagnosen mit dem erwarteten Verhalten. Verfolge den Pfad der Typverengung für isinstance(target_type, int) und target_type is int; fertig ist die Aufgabe, wenn die ungültige erste Funktion abgelehnt wird und das unterstützte Verhalten bei der Typverengung durch Regressionstests abgedeckt ist.
Vom Indexierungsmodell aus dem Issue-Text verfasst.
Bewertung
- Tech-Stack
- python
- Bereich
- compilers, devtools
- Issue-Typ
- Bug
- Schwierigkeit
- 4/5
- Geschätzter Aufwand
- 3-5 Tage
- Aktivitätsstatus
- Veraltet
- Klarheit
- Größtenteils klar
- Anfängerfreundlichkeit
- 35/100