In msgspec we have a decode function with the following signature:
def decode(msg: bytes, type: Type[T]) -> T:
...
# called like
decode(msg, dict[str, int])
This is intended to indicate that the msg should be decoded as an instance of type T, or error if invalid. In practice this works well on most types, but fails on top-level union types.
Here's a minimal reproducer:
from typing import Union, Type, TypeVar, cast
T = TypeVar("T")
def decode(msg: bytes, type: Type[T]) -> T:
return cast(T, msg) # standin for an actual decoder
o = decode(b"test", int) # This works
reveal_type(o)
reveal_type(Union[int, str]) # This is object for some reason
o = decode(b"test", Union[int, str]) # This fails
reveal_type(o)
mypy output
$ mypy test.py
test.py:11: note: Revealed type is "builtins.int"
test.py:13: note: Revealed type is "builtins.object"
test.py:15: error: Argument 2 to "decode" has incompatible type "object"; expected "Type[<nothing>]"
test.py:16: note: Revealed type is "<nothing>"
Found 1 error in 1 file (checked 1 source file)
pyright output
Just for comparison, pyright understands this code:
$ pyright test.py
No configuration file found.
No pyproject.toml file found.
stubPath /home/jcristharif/Code/msgspec/typings is not a valid directory.
Assuming Python platform Linux
Searching for source files
Found 1 source file
pyright 1.1.268
/home/jcristharif/Code/msgspec/test.py
/home/jcristharif/Code/msgspec/test.py:11:13 - information: Type of "o" is "int"
/home/jcristharif/Code/msgspec/test.py:13:13 - information: Type of "Union[int, str]" is "Type[int] | Type[str]"
/home/jcristharif/Code/msgspec/test.py:16:13 - information: Type of "o" is "int | str"
0 errors, 0 warnings, 3 informations
Completed in 0.725sec
Environment
- python 3.10
- mypy 0.971 (compiled: yes)
- Linux
In msgspec we have a
decodefunction with the following signature:This is intended to indicate that the
msgshould be decoded as an instance of typeT, or error if invalid. In practice this works well on most types, but fails on top-level union types.Here's a minimal reproducer:
mypy output
pyright output
Just for comparison,
pyrightunderstands this code:Environment