@@ -59,6 +59,7 @@ def __getitem__(self, typeargs: Any) -> object: ...
5959
6060Final = 0
6161Literal = 0
62+ NewType = 0
6263TypedDict = 0
6364
6465class TypeVar:
@@ -255,7 +256,7 @@ def test(*args: Any, **kwargs: Any) -> None:
255256 output = run_stubtest (
256257 stub = "\n \n " .join (textwrap .dedent (c .stub .lstrip ("\n " )) for c in cases ),
257258 runtime = "\n \n " .join (textwrap .dedent (c .runtime .lstrip ("\n " )) for c in cases ),
258- options = ["--generate-allowlist" ],
259+ options = ["--generate-allowlist" , "--strict-type-check-only" ],
259260 )
260261
261262 actual_errors = set (output .splitlines ())
@@ -904,8 +905,9 @@ def f(a, *args): ...
904905 def test_decorated_overload (self ) -> Iterator [Case ]:
905906 yield Case (
906907 stub = """
907- from typing import overload
908+ from typing import overload, type_check_only
908909
910+ @type_check_only
909911 class _dec1:
910912 def __init__(self, func: object) -> None: ...
911913 def __call__(self, x: str) -> str: ...
@@ -921,6 +923,7 @@ def good1(unrelated: int, whatever: str) -> str: ...
921923 )
922924 yield Case (
923925 stub = """
926+ @type_check_only
924927 class _dec2:
925928 def __init__(self, func: object) -> None: ...
926929 def __call__(self, x: str, y: int) -> str: ...
@@ -936,6 +939,7 @@ def good2(unrelated: int, whatever: str) -> str: ...
936939 )
937940 yield Case (
938941 stub = """
942+ @type_check_only
939943 class _dec3:
940944 def __init__(self, func: object) -> None: ...
941945 def __call__(self, x: str, y: int) -> str: ...
@@ -1245,7 +1249,7 @@ def test_type_alias(self) -> Iterator[Case]:
12451249 import collections.abc
12461250 import re
12471251 import typing
1248- from typing import Callable, Dict, Generic, Iterable, List, Match, Tuple, TypeVar, Union
1252+ from typing import Callable, Dict, Generic, Iterable, List, Match, Tuple, TypeVar, Union, type_check_only
12491253 """ ,
12501254 runtime = """
12511255 import collections.abc
@@ -1316,6 +1320,7 @@ class Y: ...
13161320 yield Case (
13171321 stub = """
13181322 _T = TypeVar("_T")
1323+ @type_check_only
13191324 class _Spam(Generic[_T]):
13201325 def foo(self) -> None: ...
13211326 IntFood = _Spam[int]
@@ -1693,6 +1698,7 @@ def test_missing(self) -> Iterator[Case]:
16931698 yield Case (stub = "x = 5" , runtime = "" , error = "x" )
16941699 yield Case (stub = "def f(): ..." , runtime = "" , error = "f" )
16951700 yield Case (stub = "class X: ..." , runtime = "" , error = "X" )
1701+ yield Case (stub = "class _X: ..." , runtime = "" , error = "_X" )
16961702 yield Case (
16971703 stub = """
16981704 from typing import overload
@@ -1749,6 +1755,8 @@ def __delattr__(self, name: str, /) -> None: ...
17491755 runtime = "class FakeDelattrClass: ..." ,
17501756 error = "FakeDelattrClass.__delattr__" ,
17511757 )
1758+ yield Case (stub = "from typing import NewType" , runtime = "" , error = None )
1759+ yield Case (stub = "_Int = NewType('_Int', int)" , runtime = "" , error = None )
17521760
17531761 @collect_cases
17541762 def test_missing_no_runtime_all (self ) -> Iterator [Case ]:
@@ -2375,8 +2383,9 @@ def test_special_subtype(self) -> Iterator[Case]:
23752383 )
23762384 yield Case (
23772385 stub = """
2378- from typing import TypedDict
2386+ from typing import TypedDict, type_check_only
23792387
2388+ @type_check_only
23802389 class _Options(TypedDict):
23812390 a: str
23822391 b: int
@@ -2796,6 +2805,70 @@ def func2() -> None: ...
27962805 runtime = "def func2() -> None: ..." ,
27972806 error = "func2" ,
27982807 )
2808+ # The same is true for private types
2809+ yield Case (
2810+ stub = """
2811+ @type_check_only
2812+ class _P1: ...
2813+ """ ,
2814+ runtime = "" ,
2815+ error = None ,
2816+ )
2817+ yield Case (
2818+ stub = """
2819+ @type_check_only
2820+ class _P2: ...
2821+ """ ,
2822+ runtime = "class _P2: ..." ,
2823+ error = "_P2" ,
2824+ )
2825+ # Private TypedDicts which do not exist at runtime must be decorated with
2826+ # '@type_check_only', unless they contain keys that are not valid identifiers.
2827+ yield Case (
2828+ stub = """
2829+ class _TD1(TypedDict): ...
2830+ """ ,
2831+ runtime = "" ,
2832+ error = "_TD1" ,
2833+ )
2834+ yield Case (
2835+ stub = """
2836+ _TD2 = TypedDict("_TD2", {"foo": int})
2837+ """ ,
2838+ runtime = "" ,
2839+ error = "_TD2" ,
2840+ )
2841+ yield Case (
2842+ stub = """
2843+ _TD3 = TypedDict("_TD3", {"foo-bar": int})
2844+ """ ,
2845+ runtime = "" ,
2846+ error = None ,
2847+ )
2848+ yield Case (
2849+ stub = """
2850+ _TD4 = TypedDict("_TD4", {"class": int})
2851+ """ ,
2852+ runtime = "" ,
2853+ error = None ,
2854+ )
2855+ # Private NamedTuples which do not exist at runtime must be decorated with
2856+ # '@type_check_only'.
2857+ yield Case (
2858+ stub = """
2859+ class _NT1(NamedTuple): ...
2860+ """ ,
2861+ runtime = "" ,
2862+ error = "_NT1" ,
2863+ )
2864+ yield Case (
2865+ stub = """
2866+ @type_check_only
2867+ class _NT2(NamedTuple): ...
2868+ """ ,
2869+ runtime = "" ,
2870+ error = None ,
2871+ )
27992872 # A type that exists at runtime is allowed to alias a type marked
28002873 # as '@type_check_only' in the stubs.
28012874 yield Case (
@@ -2812,8 +2885,9 @@ class _X1: ...
28122885 def test_type_default_protocol (self ) -> Iterator [Case ]:
28132886 yield Case (
28142887 stub = """
2815- from typing import Protocol
2888+ from typing import Protocol, type_check_only
28162889
2890+ @type_check_only
28172891 class _FormatterClass(Protocol):
28182892 def __call__(self, *, prog: str) -> HelpFormatter: ...
28192893
0 commit comments