| [case testSelfTypeInstance] |
| from typing import TypeVar |
| |
| T = TypeVar('T', bound='A', covariant=True) |
| |
| class A: |
| def copy(self: T) -> T: pass |
| |
| class B(A): |
| pass |
| |
| reveal_type(A().copy) # N: Revealed type is 'def () -> __main__.A*' |
| reveal_type(B().copy) # N: Revealed type is 'def () -> __main__.B*' |
| reveal_type(A().copy()) # N: Revealed type is '__main__.A*' |
| reveal_type(B().copy()) # N: Revealed type is '__main__.B*' |
| |
| [builtins fixtures/bool.pyi] |
| |
| [case testSelfTypeStaticAccess] |
| from typing import TypeVar |
| |
| T = TypeVar('T', bound='A', covariant=True) |
| class A: |
| def copy(self: T) -> T: pass |
| |
| class B(A): |
| pass |
| |
| # Erased instances appear on reveal_type; unrelated to self type |
| def f(a: A) -> None: pass |
| f(A.copy(A())) |
| f(A.copy(B())) |
| f(B.copy(B())) |
| |
| # TODO: make it an error |
| # f(B.copy(A())) |
| |
| def g(a: B) -> None: pass |
| g(A.copy(A())) # E: Argument 1 to "g" has incompatible type "A"; expected "B" |
| g(A.copy(B())) |
| g(B.copy(B())) |
| |
| [builtins fixtures/bool.pyi] |
| |
| [case testSelfTypeReturn] |
| from typing import TypeVar, Type |
| |
| R = TypeVar('R') |
| def _type(self: R) -> Type[R]: pass |
| |
| T = TypeVar('T', bound='A', covariant=True) |
| class A: |
| def copy(self: T) -> T: |
| if B(): |
| return A() # E: Incompatible return value type (got "A", expected "T") |
| elif A(): |
| return B() # E: Incompatible return value type (got "B", expected "T") |
| reveal_type(_type(self)) # N: Revealed type is 'Type[T`-1]' |
| return reveal_type(_type(self)()) # N: Revealed type is 'T`-1' |
| |
| class B(A): |
| pass |
| |
| Q = TypeVar('Q', bound='C', covariant=True) |
| class C: |
| def __init__(self, a: int) -> None: pass |
| |
| def copy(self: Q) -> Q: |
| if self: |
| return reveal_type(_type(self)(1)) # N: Revealed type is 'Q`-1' |
| else: |
| return _type(self)() # E: Too few arguments for "C" |
| |
| |
| [builtins fixtures/bool.pyi] |
| |
| [case testSelfTypeClass] |
| from typing import TypeVar, Type |
| |
| T = TypeVar('T', bound='A') |
| |
| class A: |
| @classmethod |
| def new(cls: Type[T]) -> T: |
| return reveal_type(cls()) # N: Revealed type is 'T`-1' |
| |
| class B(A): |
| pass |
| |
| Q = TypeVar('Q', bound='C', covariant=True) |
| class C: |
| def __init__(self, a: int) -> None: pass |
| |
| @classmethod |
| def new(cls: Type[Q]) -> Q: |
| if cls: |
| return cls(1) |
| else: |
| return cls() # E: Too few arguments for "C" |
| |
| |
| reveal_type(A.new) # N: Revealed type is 'def () -> __main__.A*' |
| reveal_type(B.new) # N: Revealed type is 'def () -> __main__.B*' |
| reveal_type(A.new()) # N: Revealed type is '__main__.A*' |
| reveal_type(B.new()) # N: Revealed type is '__main__.B*' |
| |
| [builtins fixtures/classmethod.pyi] |
| |
| [case testSelfTypeOverride] |
| from typing import TypeVar, cast |
| |
| T = TypeVar('T', bound='A', covariant=True) |
| |
| class A: |
| def copy(self: T) -> T: pass |
| |
| class B(A): |
| pass |
| |
| Q = TypeVar('Q', bound='C', covariant=True) |
| class C(A): |
| def copy(self: Q) -> Q: pass |
| |
| reveal_type(C().copy) # N: Revealed type is 'def () -> __main__.C*' |
| reveal_type(C().copy()) # N: Revealed type is '__main__.C*' |
| reveal_type(cast(A, C()).copy) # N: Revealed type is 'def () -> __main__.A*' |
| reveal_type(cast(A, C()).copy()) # N: Revealed type is '__main__.A*' |
| |
| [builtins fixtures/bool.pyi] |
| |
| [case testSelfTypeSuper] |
| from typing import TypeVar, cast |
| |
| T = TypeVar('T', bound='A', covariant=True) |
| |
| class A: |
| def copy(self: T) -> T: pass |
| |
| Q = TypeVar('Q', bound='B', covariant=True) |
| class B(A): |
| def copy(self: Q) -> Q: |
| reveal_type(self) # N: Revealed type is 'Q`-1' |
| reveal_type(super().copy) # N: Revealed type is 'def () -> Q`-1' |
| return super().copy() |
| |
| [builtins fixtures/bool.pyi] |
| |
| [case testSelfTypeRecursiveBinding] |
| from typing import TypeVar, Callable, Type |
| |
| T = TypeVar('T', bound='A', covariant=True) |
| class A: |
| # TODO: This is potentially unsafe, as we use T in an argument type |
| def copy(self: T, factory: Callable[[T], T]) -> T: |
| return factory(self) |
| |
| @classmethod |
| def new(cls: Type[T], factory: Callable[[T], T]) -> T: |
| reveal_type(cls) # N: Revealed type is 'Type[T`-1]' |
| reveal_type(cls()) # N: Revealed type is 'T`-1' |
| cls(2) # E: Too many arguments for "A" |
| return cls() |
| |
| class B(A): |
| pass |
| |
| reveal_type(A().copy) # N: Revealed type is 'def (factory: def (__main__.A*) -> __main__.A*) -> __main__.A*' |
| reveal_type(B().copy) # N: Revealed type is 'def (factory: def (__main__.B*) -> __main__.B*) -> __main__.B*' |
| reveal_type(A.new) # N: Revealed type is 'def (factory: def (__main__.A*) -> __main__.A*) -> __main__.A*' |
| reveal_type(B.new) # N: Revealed type is 'def (factory: def (__main__.B*) -> __main__.B*) -> __main__.B*' |
| |
| [builtins fixtures/classmethod.pyi] |
| |
| [case testSelfTypeBound] |
| from typing import TypeVar, Callable, cast |
| |
| TA = TypeVar('TA', bound='A', covariant=True) |
| |
| class A: |
| def copy(self: TA) -> TA: |
| pass |
| |
| class C(A): |
| def copy(self: C) -> C: |
| pass |
| |
| class D(A): |
| def copy(self: A) -> A: # E: Return type "A" of "copy" incompatible with return type "D" in supertype "A" |
| pass |
| |
| TB = TypeVar('TB', bound='B', covariant=True) |
| class B(A): |
| x = 1 |
| def copy(self: TB) -> TB: |
| reveal_type(self.x) # N: Revealed type is 'builtins.int' |
| return cast(TB, None) |
| |
| [builtins fixtures/bool.pyi] |
| |
| -- # TODO: fail for this |
| -- [case testSelfTypeBare] |
| -- from typing import TypeVar, Type |
| -- |
| -- T = TypeVar('T', bound='E') |
| -- |
| -- class E: |
| -- def copy(self: T, other: T) -> T: pass |
| |
| [case testSelfTypeClone] |
| from typing import TypeVar, Type |
| T = TypeVar('T', bound='C') |
| |
| class C: |
| def copy(self: T) -> T: |
| return self |
| |
| @classmethod |
| def new(cls: Type[T]) -> T: |
| return cls() |
| |
| class D(C): pass |
| |
| reveal_type(D.new) # N: Revealed type is 'def () -> __main__.D*' |
| reveal_type(D().new) # N: Revealed type is 'def () -> __main__.D*' |
| reveal_type(D.new()) # N: Revealed type is '__main__.D*' |
| reveal_type(D().new()) # N: Revealed type is '__main__.D*' |
| |
| Q = TypeVar('Q', bound=C) |
| |
| def clone(arg: Q) -> Q: |
| reveal_type(arg.copy) # N: Revealed type is 'def () -> Q`-1' |
| reveal_type(arg.copy()) # N: Revealed type is 'Q`-1' |
| reveal_type(arg.new) # N: Revealed type is 'def () -> Q`-1' |
| reveal_type(arg.new()) # N: Revealed type is 'Q`-1' |
| return arg.copy() |
| |
| def make(cls: Type[Q]) -> Q: |
| reveal_type(cls.new) # N: Revealed type is 'def () -> Q`-1' |
| reveal_type(cls().new) # N: Revealed type is 'def () -> Q`-1' |
| reveal_type(cls().new()) # N: Revealed type is 'Q`-1' |
| return cls.new() |
| |
| [builtins fixtures/classmethod.pyi] |
| |
| [case testSelfTypeGeneric] |
| from typing import TypeVar |
| |
| T = TypeVar('T', int, str) |
| |
| class A: |
| pass |
| |
| class B(A): |
| def __init__(self, arg: T) -> None: |
| super(B, self).__init__() |
| |
| [case testSelfTypeNonsensical] |
| from typing import TypeVar, Type |
| |
| T = TypeVar('T', bound=str) |
| class A: |
| def foo(self: T) -> T: # E: The erased type of self "builtins.str" is not a supertype of its class "__main__.A" |
| return self |
| |
| @classmethod |
| def cfoo(cls: Type[T]) -> T: # E: The erased type of self "Type[builtins.str]" is not a supertype of its class "Type[__main__.A]" |
| return cls() |
| |
| Q = TypeVar('Q', bound='B') |
| class B: |
| def foo(self: Q) -> Q: |
| return self |
| |
| @classmethod |
| def cfoo(cls: Type[Q]) -> Q: |
| return cls() |
| |
| class C: |
| def foo(self: C) -> C: return self |
| |
| @classmethod |
| def cfoo(cls: Type[C]) -> C: |
| return cls() |
| |
| class D: |
| def foo(self: Q) -> Q: # E: The erased type of self "__main__.B" is not a supertype of its class "__main__.D" |
| return self |
| |
| @staticmethod |
| def bar(self: str) -> str: |
| return self |
| |
| @classmethod |
| def cfoo(cls: Type[Q]) -> Q: # E: The erased type of self "Type[__main__.B]" is not a supertype of its class "Type[__main__.D]" |
| return cls() |
| |
| [builtins fixtures/classmethod.pyi] |
| |
| [case testSelfTypeLambdaDefault] |
| from typing import Callable |
| class C: |
| @classmethod |
| def foo(cls, |
| arg: Callable[[int], str] = lambda a: '' |
| ) -> None: |
| pass |
| |
| def bar(self, |
| arg: Callable[[int], str] = lambda a: '' |
| ) -> None: |
| pass |
| [builtins fixtures/classmethod.pyi] |
| |
| [case testSelfTypeNew] |
| from typing import TypeVar, Type |
| |
| T = TypeVar('T', bound=A) |
| class A: |
| def __new__(cls: Type[T]) -> T: |
| return cls() |
| |
| def __init_subclass__(cls: Type[T]) -> None: |
| pass |
| |
| class B: |
| def __new__(cls: Type[T]) -> T: # E: The erased type of self "Type[__main__.A]" is not a supertype of its class "Type[__main__.B]" |
| return cls() |
| |
| def __init_subclass__(cls: Type[T]) -> None: # E: The erased type of self "Type[__main__.A]" is not a supertype of its class "Type[__main__.B]" |
| pass |
| |
| class C: |
| def __new__(cls: Type[C]) -> C: |
| return cls() |
| |
| def __init_subclass__(cls: Type[C]) -> None: |
| pass |
| |
| class D: |
| def __new__(cls: D) -> D: # E: The erased type of self "__main__.D" is not a supertype of its class "Type[__main__.D]" |
| return cls |
| |
| def __init_subclass__(cls: D) -> None: # E: The erased type of self "__main__.D" is not a supertype of its class "Type[__main__.D]" |
| pass |
| |
| class E: |
| def __new__(cls) -> E: |
| reveal_type(cls) # N: Revealed type is 'Type[__main__.E]' |
| return cls() |
| |
| def __init_subclass__(cls) -> None: |
| reveal_type(cls) # N: Revealed type is 'Type[__main__.E]' |
| |
| [case testSelfTypePropertyUnion] |
| from typing import Union |
| class A: |
| @property |
| def f(self: A) -> int: pass |
| |
| class B: |
| @property |
| def f(self: B) -> int: pass |
| x: Union[A, B] |
| reveal_type(x.f) # N: Revealed type is 'builtins.int' |
| |
| [builtins fixtures/property.pyi] |
| |
| [case testSelfTypeProperSupertypeAttribute] |
| from typing import Callable, TypeVar |
| class K: pass |
| T = TypeVar('T', bound=K) |
| class A(K): |
| @property |
| def g(self: K) -> int: return 0 |
| @property |
| def gt(self: T) -> T: return self |
| f: Callable[[object], int] |
| ft: Callable[[T], T] |
| |
| class B(A): |
| pass |
| |
| reveal_type(A().g) # N: Revealed type is 'builtins.int' |
| reveal_type(A().gt) # N: Revealed type is '__main__.A*' |
| reveal_type(A().f()) # N: Revealed type is 'builtins.int' |
| reveal_type(A().ft()) # N: Revealed type is '__main__.A*' |
| reveal_type(B().g) # N: Revealed type is 'builtins.int' |
| reveal_type(B().gt) # N: Revealed type is '__main__.B*' |
| reveal_type(B().f()) # N: Revealed type is 'builtins.int' |
| reveal_type(B().ft()) # N: Revealed type is '__main__.B*' |
| |
| [builtins fixtures/property.pyi] |
| |
| [case testSelfTypeProperSupertypeAttributeTuple] |
| from typing import Callable, TypeVar, Tuple |
| T = TypeVar('T') |
| class A(Tuple[int, int]): |
| @property |
| def g(self: object) -> int: return 0 |
| @property |
| def gt(self: T) -> T: return self |
| f: Callable[[object], int] |
| ft: Callable[[T], T] |
| |
| class B(A): |
| pass |
| |
| reveal_type(A().g) # N: Revealed type is 'builtins.int' |
| reveal_type(A().gt) # N: Revealed type is 'Tuple[builtins.int, builtins.int, fallback=__main__.A]' |
| reveal_type(A().f()) # N: Revealed type is 'builtins.int' |
| reveal_type(A().ft()) # N: Revealed type is 'Tuple[builtins.int, builtins.int, fallback=__main__.A]' |
| reveal_type(B().g) # N: Revealed type is 'builtins.int' |
| reveal_type(B().gt) # N: Revealed type is 'Tuple[builtins.int, builtins.int, fallback=__main__.B]' |
| reveal_type(B().f()) # N: Revealed type is 'builtins.int' |
| reveal_type(B().ft()) # N: Revealed type is 'Tuple[builtins.int, builtins.int, fallback=__main__.B]' |
| |
| [builtins fixtures/property.pyi] |
| |
| [case testSelfTypeProperSupertypeAttributeMeta] |
| from typing import Callable, TypeVar, Type |
| T = TypeVar('T') |
| class A(type): |
| @property |
| def g(cls: object) -> int: return 0 |
| @property |
| def gt(cls: T) -> T: return cls |
| f: Callable[[object], int] |
| ft: Callable[[T], T] |
| |
| class B(A): |
| pass |
| |
| class X(metaclass=B): |
| def __init__(self, x: int) -> None: pass |
| class Y(X): pass |
| X1: Type[X] |
| reveal_type(X.g) # N: Revealed type is 'builtins.int' |
| reveal_type(X.gt) # N: Revealed type is 'def (x: builtins.int) -> __main__.X' |
| reveal_type(X.f()) # N: Revealed type is 'builtins.int' |
| reveal_type(X.ft()) # N: Revealed type is 'def (x: builtins.int) -> __main__.X' |
| reveal_type(Y.g) # N: Revealed type is 'builtins.int' |
| reveal_type(Y.gt) # N: Revealed type is 'def (x: builtins.int) -> __main__.Y' |
| reveal_type(Y.f()) # N: Revealed type is 'builtins.int' |
| reveal_type(Y.ft()) # N: Revealed type is 'def (x: builtins.int) -> __main__.Y' |
| reveal_type(X1.g) # N: Revealed type is 'builtins.int' |
| reveal_type(X1.gt) # N: Revealed type is 'Type[__main__.X]' |
| reveal_type(X1.f()) # N: Revealed type is 'builtins.int' |
| reveal_type(X1.ft()) # N: Revealed type is 'Type[__main__.X]' |
| |
| [builtins fixtures/property.pyi] |
| |
| [case testSelfTypeProperSupertypeAttributeGeneric] |
| from typing import Callable, TypeVar, Generic |
| Q = TypeVar('Q', covariant=True) |
| class K(Generic[Q]): |
| q: Q |
| T = TypeVar('T') |
| class A(K[Q]): |
| @property |
| def g(self: K[object]) -> int: return 0 |
| @property |
| def gt(self: K[T]) -> T: return self.q |
| f: Callable[[object], int] |
| ft: Callable[[T], T] |
| |
| class B(A[Q]): |
| pass |
| a: A[int] |
| b: B[str] |
| reveal_type(a.g) # N: Revealed type is 'builtins.int' |
| --reveal_type(a.gt) # N: Revealed type is 'builtins.int' |
| reveal_type(a.f()) # N: Revealed type is 'builtins.int' |
| reveal_type(a.ft()) # N: Revealed type is '__main__.A*[builtins.int]' |
| reveal_type(b.g) # N: Revealed type is 'builtins.int' |
| --reveal_type(b.gt) # N: Revealed type is '__main__.B*[builtins.str]' |
| reveal_type(b.f()) # N: Revealed type is 'builtins.int' |
| reveal_type(b.ft()) # N: Revealed type is '__main__.B*[builtins.str]' |
| |
| [builtins fixtures/property.pyi] |
| |
| [case testSelfTypeNotSelfType] |
| # Friendlier error messages for common mistakes. See #2950 |
| class A: |
| def f(x: int) -> None: ... |
| # def g(self: None) -> None: ... see in check-python2.test |
| [out] |
| main:3: error: Self argument missing for a non-static method (or an invalid type for self) |
| |
| [case testUnionPropertyField] |
| from typing import Union |
| |
| class A: |
| x: int |
| |
| class B: |
| @property |
| def x(self) -> int: return 1 |
| |
| class C: |
| @property |
| def x(self) -> int: return 1 |
| |
| ab: Union[A, B, C] |
| reveal_type(ab.x) # N: Revealed type is 'builtins.int' |
| [builtins fixtures/property.pyi] |
| |
| [case testSelfTypeOnUnion] |
| from typing import TypeVar, Union |
| |
| T = TypeVar('T') |
| |
| class A: |
| same: int |
| |
| class C: |
| def same(self: T) -> T: ... |
| |
| x: Union[A, C] |
| reveal_type(x.same) # N: Revealed type is 'Union[builtins.int, def () -> __main__.C*]' |
| |
| [case testSelfTypeOnUnionClassMethod] |
| from typing import TypeVar, Union, Type |
| |
| T = TypeVar('T') |
| |
| class A: |
| same: int |
| |
| class C: |
| @classmethod |
| def same(cls: Type[T]) -> T: ... |
| |
| x: Union[A, C] |
| reveal_type(x.same) # N: Revealed type is 'Union[builtins.int, def () -> __main__.C*]' |
| [builtins fixtures/classmethod.pyi] |
| |
| [case SelfTypeOverloadedClassMethod] |
| from lib import Base |
| from typing import overload, Tuple |
| |
| class Sub(Base): |
| @overload |
| @classmethod |
| def make(cls) -> Sub: ... |
| @overload |
| @classmethod |
| def make(cls, num: int) -> Tuple[Sub, ...]: ... |
| @classmethod |
| def make(cls, num=1): |
| ... |
| |
| class Other(Base): ... |
| class Double(Sub): ... |
| |
| reveal_type(Other.make()) # N: Revealed type is '__main__.Other*' |
| reveal_type(Other.make(3)) # N: Revealed type is 'builtins.tuple[__main__.Other*]' |
| reveal_type(Double.make()) # N: Revealed type is '__main__.Sub' |
| reveal_type(Double.make(3)) # N: Revealed type is 'builtins.tuple[__main__.Sub]' |
| [file lib.pyi] |
| from typing import overload, TypeVar, Type, Tuple |
| |
| T = TypeVar('T', bound=Base) |
| |
| class Base: |
| @overload |
| @classmethod |
| def make(cls: Type[T]) -> T: ... |
| @overload |
| @classmethod |
| def make(cls: Type[T], num: int) -> Tuple[T, ...]: ... |
| [builtins fixtures/classmethod.pyi] |
| |
| [case testSelfTypeClassMethodOnUnion] |
| from typing import Type, Union, TypeVar |
| |
| T = TypeVar('T') |
| |
| class A: |
| @classmethod |
| def meth(cls: Type[T]) -> T: ... |
| class B(A): ... |
| class C(A): ... |
| |
| t: Type[Union[B, C]] |
| reveal_type(t.meth) # N: Revealed type is 'Union[def () -> __main__.B*, def () -> __main__.C*]' |
| x = t.meth() |
| reveal_type(x) # N: Revealed type is 'Union[__main__.B*, __main__.C*]' |
| [builtins fixtures/classmethod.pyi] |
| |
| [case testSelfTypeClassMethodOnUnionGeneric] |
| from typing import Type, Union, TypeVar, Generic |
| |
| T = TypeVar('T') |
| S = TypeVar('S') |
| |
| class A(Generic[T]): |
| @classmethod |
| def meth(cls: Type[S]) -> S: ... |
| |
| t: Type[Union[A[int], A[str]]] |
| x = t.meth() |
| reveal_type(x) # N: Revealed type is 'Union[__main__.A*[builtins.int], __main__.A*[builtins.str]]' |
| [builtins fixtures/classmethod.pyi] |
| |
| [case testSelfTypeClassMethodOnUnionList] |
| from typing import Type, Union, TypeVar, List |
| |
| T = TypeVar('T') |
| |
| class A: |
| @classmethod |
| def meth(cls: Type[T]) -> List[T]: ... |
| class B(A): ... |
| class C(A): ... |
| |
| t: Type[Union[B, C]] |
| x = t.meth()[0] |
| reveal_type(x) # N: Revealed type is 'Union[__main__.B*, __main__.C*]' |
| [builtins fixtures/isinstancelist.pyi] |