pyre-check
pyre-check copied to clipboard
Support unpacked arbitrary-length tuple in type argument lists
Pyre Bug
PEP 646 specifies that the following behaviour should be valid:
T = TypeVar('T')
Ts = TypeVarTuple('Ts')
class C(Generic[T, *Ts]): pass
C[*tuple[int, ...]]
I think Pyre doesn't handle this correctly yet. For example:
from typing import Generic, TypeVar
from pyre_extensions import Unpack, TypeVarTuple
T = TypeVar('T')
Ts = TypeVarTuple('Ts')
class C(Generic[T, Unpack[Ts]]): ...
x: C[Unpack[tuple[int, ...]]] = C()
reveal_type(x)
ƛ Found 2 type errors!
foo.py:9:3 Invalid type parameters [24]: Generic type `C` expects at least 1 type parameter, received 1.
foo.py:10:0 Revealed type [-1]: Revealed type for `x` is `C[typing.Any, *Tuple[typing.Any, ...]]`.
Similarly, the following should be valid with type aliases:
Alias = tuple[T, *Ts]
Alias[*tuple[int, ...]]
With Pyre:
from typing import Generic, TypeVar
from pyre_extensions import Unpack, TypeVarTuple
T = TypeVar('T')
Ts = TypeVarTuple('Ts')
Alias = tuple[T, Unpack[Ts]]
x: Alias[Unpack[tuple[int, ...]]] = (1, 2, 3)
reveal_type(x)
foo2.py:9:3 Invalid type variable [34]: The type variable `Variable[T]` can only be used to annotate generic classes or functions.
foo2.py:9:3 Invalid type variable [34]: The type variable `Ts` can only be used to annotate generic classes or functions.
foo2.py:10:0 Revealed type [-1]: Revealed type for `x` is `typing.Tuple[typing_extensions.Literal[1], typing_extensions.Literal[2], typing_extensions.Literal[3]]`.
@pradeep90 I think this is yours too?