106106# legitimate imports of those modules.
107107
108108
109- def _type_check (arg , msg ):
109+ def _type_check (arg , msg , is_argument = False ):
110110 """Check that the argument is a type, and return it (internal helper).
111111
112112 As a special case, accept None and return type(None) instead. Also wrap strings
@@ -118,12 +118,16 @@ def _type_check(arg, msg):
118118
119119 We append the repr() of the actual value (truncated to 100 chars).
120120 """
121+ invalid_generic_forms = (Generic , _Protocol )
122+ if not is_argument :
123+ invalid_generic_forms = invalid_generic_forms + (ClassVar , )
124+
121125 if arg is None :
122126 return type (None )
123127 if isinstance (arg , str ):
124128 return ForwardRef (arg )
125129 if (isinstance (arg , _GenericAlias ) and
126- arg .__origin__ in ( Generic , _Protocol , ClassVar ) ):
130+ arg .__origin__ in invalid_generic_forms ):
127131 raise TypeError (f"{ arg } is not valid as type argument" )
128132 if (isinstance (arg , _SpecialForm ) and arg is not Any or
129133 arg in (Generic , _Protocol )):
@@ -464,9 +468,10 @@ class ForwardRef(_Final, _root=True):
464468 """Internal wrapper to hold a forward reference."""
465469
466470 __slots__ = ('__forward_arg__' , '__forward_code__' ,
467- '__forward_evaluated__' , '__forward_value__' )
471+ '__forward_evaluated__' , '__forward_value__' ,
472+ '__forward_is_argument__' )
468473
469- def __init__ (self , arg ):
474+ def __init__ (self , arg , is_argument = False ):
470475 if not isinstance (arg , str ):
471476 raise TypeError (f"Forward reference must be a string -- got { arg !r} " )
472477 try :
@@ -477,6 +482,7 @@ def __init__(self, arg):
477482 self .__forward_code__ = code
478483 self .__forward_evaluated__ = False
479484 self .__forward_value__ = None
485+ self .__forward_is_argument__ = is_argument
480486
481487 def _evaluate (self , globalns , localns ):
482488 if not self .__forward_evaluated__ or localns is not globalns :
@@ -488,7 +494,8 @@ def _evaluate(self, globalns, localns):
488494 localns = globalns
489495 self .__forward_value__ = _type_check (
490496 eval (self .__forward_code__ , globalns , localns ),
491- "Forward references must evaluate to types." )
497+ "Forward references must evaluate to types." ,
498+ is_argument = self .__forward_is_argument__ )
492499 self .__forward_evaluated__ = True
493500 return self .__forward_value__
494501
@@ -998,7 +1005,7 @@ def get_type_hints(obj, globalns=None, localns=None):
9981005 if value is None :
9991006 value = type (None )
10001007 if isinstance (value , str ):
1001- value = ForwardRef (value )
1008+ value = ForwardRef (value , is_argument = True )
10021009 value = _eval_type (value , base_globals , localns )
10031010 hints [name ] = value
10041011 return hints
0 commit comments