Prerequisite: This issue applies after PR #19596 is merged.
Currently mypy sometimes allows a type variable to be assigned to a TypeForm variable and sometimes it does not. This is a problem because the behavior is inconsistent.
Specifically, mypy allows a type variable to be assigned to a TypeForm variable iff it is in a quoted type expression:
[casetestTypeVarTypeFormsAreOnlyRecognizedInStringAnnotation]
...
E=TypeVar('E')
classBox(Generic[E]):
deffoo(self, e: E) ->None:
list_of_typx: List[TypeForm] = [E] # E: "E" is a type variable and only valid in type contexttypx1: TypeForm=E# E: "E" is a type variable and only valid in type contexttypx2: TypeForm='E'When a type variable is NOT quoted, mypy will not allow it to be assigned:
[casetestEveryKindOfTypeExpressionIsAssignableToATypeFormVariable]
SomeTypeVar=TypeVar('SomeTypeVar')
typx: TypeForm
...
# NOTE: Unbound TypeVar isn't currently accepted as a TypeForm. Is that OK?typx=SomeTypeVar# E: Incompatible types in assignment (expression has type "TypeVar", variable has type "TypeForm[Any]")I'd argue that TypeForm should always accept a type variable because it is a valid type expression and TypeForms are intended to accept all kinds of type expressions:
def cast[T](type_expr: TypeForm[T], value_expr: object) -> T: ...
cast(SomeTypeVar, some_expression) # should not be an error
In summary:
Currently mypy sometimes allows a type variable to be assigned to a TypeForm variable and sometimes it does not. This is a problem because the behavior is inconsistent.
Specifically, mypy allows a type variable to be assigned to a TypeForm variable iff it is in a quoted type expression:
When a type variable is NOT quoted, mypy will not allow it to be assigned:
I'd argue that TypeForm should always accept a type variable because it is a valid type expression and TypeForms are intended to accept all kinds of type expressions:
In summary: