1212
1313from __future__ import annotations
1414
15- from typing import TYPE_CHECKING , Any
15+ from typing import TYPE_CHECKING , Any , TypeAlias
1616
1717from astroid import nodes
1818
2323if TYPE_CHECKING :
2424 from pylint .lint import PyLinter
2525
26+ SimpleNode : TypeAlias = (
27+ nodes .Assert
28+ | nodes .Assign
29+ | nodes .AugAssign
30+ | nodes .Delete
31+ | nodes .Raise
32+ | nodes .Yield
33+ | nodes .Import
34+ | nodes .Call
35+ | nodes .Subscript
36+ | nodes .Pass
37+ | nodes .Continue
38+ | nodes .Break
39+ | nodes .Global
40+ | nodes .Return
41+ | nodes .Expr
42+ | nodes .Await
43+ )
44+
2645
2746class PathGraph :
2847 def __init__ (self ) -> None :
@@ -58,14 +77,42 @@ def __init__(self) -> None:
5877 self .tail : Any = None
5978
6079 def dispatch (self , node : nodes .NodeNG ) -> None :
61- meth = getattr (self , "visit" + node .__class__ .__name__ , self .default )
62- meth (node )
80+ {
81+ "FunctionDef" : self .visitFunctionDef ,
82+ "AsyncFunctionDef" : self .visitFunctionDef ,
83+ "With" : self .visitWith ,
84+ "AsyncWith" : self .visitWith ,
85+ "For" : self .visitFor ,
86+ "AsyncFor" : self .visitFor ,
87+ "While" : self .visitFor ,
88+ "If" : self .visitFor ,
89+ "Try" : self .visitTry ,
90+ "Match" : self .visitMatch ,
91+ "Assert" : self .visitSimpleNode ,
92+ "Assign" : self .visitSimpleNode ,
93+ "AugAssign" : self .visitSimpleNode ,
94+ "Delete" : self .visitSimpleNode ,
95+ "Raise" : self .visitSimpleNode ,
96+ "Yield" : self .visitSimpleNode ,
97+ "Import" : self .visitSimpleNode ,
98+ "Call" : self .visitSimpleNode ,
99+ "Subscript" : self .visitSimpleNode ,
100+ "Pass" : self .visitSimpleNode ,
101+ "Continue" : self .visitSimpleNode ,
102+ "Break" : self .visitSimpleNode ,
103+ "Global" : self .visitSimpleNode ,
104+ "Return" : self .visitSimpleNode ,
105+ "Expr" : self .visitSimpleNode ,
106+ "Await" : self .visitSimpleNode ,
107+ }.get (node .__class__ .__name__ , self .default )(node )
63108
64109 def default (self , node : nodes .NodeNG ) -> None :
65110 for child in node .get_children ():
66111 self .dispatch (child )
67112
68- def visitFunctionDef (self , node : nodes .FunctionDef ) -> None :
113+ def visitFunctionDef (
114+ self , node : nodes .FunctionDef | nodes .AsyncFunctionDef
115+ ) -> None :
69116 if self .graph is not None :
70117 # closure
71118 self .graph .connect (self .tail , node )
@@ -86,33 +133,23 @@ def visitFunctionDef(self, node: nodes.FunctionDef) -> None:
86133 self .graph = None
87134 self .tail = None
88135
89- visitAsyncFunctionDef = visitFunctionDef
90-
91- def visitAssert (self , node : nodes .NodeNG ) -> None :
136+ def visitSimpleNode (self , node : SimpleNode ) -> None :
92137 if self .tail and self .graph :
93138 self .graph .connect (self .tail , node )
94139 self .tail = node
95140
96- visitAssign = visitAugAssign = visitDelete = visitRaise = visitYield = (
97- visitImport
98- ) = visitCall = visitSubscript = visitPass = visitContinue = visitBreak = (
99- visitGlobal
100- ) = visitReturn = visitExpr = visitAwait = visitAssert
101-
102- def visitWith (self , node : nodes .With ) -> None :
141+ def visitWith (self , node : nodes .With | nodes .AsyncWith ) -> None :
103142 if self .tail and self .graph :
104143 self .graph .connect (self .tail , node )
105144 self .tail = node
106145 for child in node .body :
107146 self .dispatch (child )
108147
109- visitAsyncWith = visitWith
110-
111- def visitFor ( self , node : nodes . For | nodes . While ) -> None :
148+ def visitFor (
149+ self , node : nodes . For | nodes . AsyncFor | nodes . While | nodes . If
150+ ) -> None :
112151 self ._subgraph (node , node .handlers if isinstance (node , nodes .Try ) else [])
113152
114- visitAsyncFor = visitWhile = visitIf = visitFor
115-
116153 def visitTry (self , node : nodes .Try ) -> None :
117154 self ._subgraph (node , node .handlers )
118155
0 commit comments