@@ -1678,28 +1678,79 @@ def CALL(self, node):
1678
1678
):
1679
1679
self ._handle_string_dot_format (node )
1680
1680
1681
+ omit = []
1682
+ annotated = []
1683
+ not_annotated = []
1684
+
1681
1685
if (
1682
1686
_is_typing (node .func , 'cast' , self .scopeStack ) and
1683
- len (node .args ) >= 1 and
1684
- isinstance (node .args [0 ], ast .Str )
1687
+ len (node .args ) >= 1
1685
1688
):
1686
- with self ._enter_annotation (AnnotationState . STRING ):
1689
+ with self ._enter_annotation ():
1687
1690
self .handleNode (node .args [0 ], node )
1688
1691
1689
1692
elif _is_typing (node .func , 'TypeVar' , self .scopeStack ):
1693
+
1690
1694
# TypeVar("T", "int", "str")
1691
- for arg in node .args [1 :]:
1692
- if isinstance (arg , ast .Str ):
1693
- with self ._enter_annotation ():
1694
- self .handleNode (arg , node )
1695
+ omit += ["args" ]
1696
+ annotated += [arg for arg in node .args [1 :]]
1695
1697
1696
1698
# TypeVar("T", bound="str")
1697
- for keyword in node .keywords :
1698
- if keyword .arg == 'bound' and isinstance (keyword .value , ast .Str ):
1699
- with self ._enter_annotation ():
1700
- self .handleNode (keyword .value , node )
1699
+ omit += ["keywords" ]
1700
+ annotated += [k .value for k in node .keywords if k .arg == "bound" ]
1701
+ not_annotated += [
1702
+ (k , ["value" ] if k .arg == "bound" else None )
1703
+ for k in node .keywords
1704
+ ]
1705
+
1706
+ elif _is_typing (node .func , "TypedDict" , self .scopeStack ):
1707
+ # TypedDict("a", {"a": int})
1708
+ if len (node .args ) > 1 and isinstance (node .args [1 ], ast .Dict ):
1709
+ omit += ["args" ]
1710
+ annotated += node .args [1 ].values
1711
+ not_annotated += [
1712
+ (arg , ["values" ] if i == 1 else None )
1713
+ for i , arg in enumerate (node .args )
1714
+ ]
1701
1715
1702
- self .handleChildren (node )
1716
+ # TypedDict("a", a=int)
1717
+ omit += ["keywords" ]
1718
+ annotated += [k .value for k in node .keywords ]
1719
+ not_annotated += [(k , ["value" ]) for k in node .keywords ]
1720
+
1721
+ elif _is_typing (node .func , "NamedTuple" , self .scopeStack ):
1722
+ # NamedTuple("a", [("a", int)])
1723
+ if (
1724
+ len (node .args ) > 1 and
1725
+ isinstance (node .args [1 ], (ast .Tuple , ast .List )) and
1726
+ all (isinstance (x , (ast .Tuple , ast .List )) and
1727
+ len (x .elts ) == 2 for x in node .args [1 ].elts )
1728
+ ):
1729
+ omit += ["args" ]
1730
+ annotated += [elt .elts [1 ] for elt in node .args [1 ].elts ]
1731
+ not_annotated += [(elt .elts [0 ], None ) for elt in node .args [1 ].elts ]
1732
+ not_annotated += [
1733
+ (arg , ["elts" ] if i == 1 else None )
1734
+ for i , arg in enumerate (node .args )
1735
+ ]
1736
+ not_annotated += [(elt , "elts" ) for elt in node .args [1 ].elts ]
1737
+
1738
+ # NamedTuple("a", a=int)
1739
+ omit += ["keywords" ]
1740
+ annotated += [k .value for k in node .keywords ]
1741
+ not_annotated += [(k , ["value" ]) for k in node .keywords ]
1742
+
1743
+ if omit :
1744
+ with self ._enter_annotation (AnnotationState .NONE ):
1745
+ for na_node , na_omit in not_annotated :
1746
+ self .handleChildren (na_node , omit = na_omit )
1747
+ self .handleChildren (node , omit = omit )
1748
+
1749
+ with self ._enter_annotation ():
1750
+ for annotated_node in annotated :
1751
+ self .handleNode (annotated_node , node )
1752
+ else :
1753
+ self .handleChildren (node )
1703
1754
1704
1755
def _handle_percent_format (self , node ):
1705
1756
try :
0 commit comments