qlty_analysis/code/
visitor.rs1use crate::Language;
2use tree_sitter::{Node, TreeCursor};
3
4pub trait Visitor {
5 fn process_node(&mut self, cursor: &mut TreeCursor) {
6 let node = cursor.node();
7 let kind = node.kind();
8 let language = self.language();
9
10 if self.skip_node(&node) {
11 return;
12 }
13
14 if language.invisible_container_nodes().contains(&kind) {
15 self.visit_invisible_container(cursor);
16 } else if language.if_nodes().contains(&kind) {
17 self.visit_if(cursor);
18 } else if language.elsif_nodes().contains(&kind) {
19 self.visit_elsif(cursor);
20 } else if language.else_nodes().contains(&kind) {
21 self.visit_else(cursor);
22 } else if language.conditional_assignment_nodes().contains(&kind) {
23 self.visit_conditional_assignment(cursor);
24 } else if language.ternary_nodes().contains(&kind) {
25 self.visit_ternary(cursor);
26 } else if language.switch_nodes().contains(&kind) {
27 self.visit_switch(cursor);
28 } else if language.case_nodes().contains(&kind) {
29 self.visit_case(cursor);
30 } else if language.loop_nodes().contains(&kind) {
31 self.visit_loop(cursor);
32 } else if language.except_nodes().contains(&kind) {
33 self.visit_except(cursor);
34 } else if language.try_expression_nodes().contains(&kind) {
35 self.visit_try_expression(cursor);
36 } else if language.jump_nodes().contains(&kind) {
37 self.visit_jump(cursor);
38 } else if language.return_nodes().contains(&kind) {
39 self.visit_return(cursor);
40 } else if language.binary_nodes().contains(&kind) {
41 self.visit_binary(cursor);
42 } else if language.field_nodes().contains(&kind) {
43 self.visit_field(cursor);
44 } else if language.call_nodes().contains(&kind) {
45 self.visit_call(cursor);
46 } else if language.function_nodes().contains(&kind) {
47 self.visit_function(cursor);
48 } else if language.closure_nodes().contains(&kind) {
49 self.visit_closure(cursor);
50 } else if language.comment_nodes().contains(&kind) {
51 self.visit_comment(cursor);
52 } else if language.string_nodes().contains(&kind) {
53 self.visit_string(cursor);
54 } else if language.block_nodes().contains(&kind) {
55 self.visit_block(cursor);
56 } else {
57 self.visit_unknown(cursor);
58 }
59 }
60
61 fn visit_invisible_container(&mut self, cursor: &mut TreeCursor) {
62 self.process_children(cursor);
63 }
64
65 fn visit_if(&mut self, cursor: &mut TreeCursor) {
66 self.process_children(cursor);
67 }
68
69 fn visit_elsif(&mut self, cursor: &mut TreeCursor) {
70 self.process_children(cursor);
71 }
72
73 fn visit_else(&mut self, cursor: &mut TreeCursor) {
74 self.process_children(cursor);
75 }
76
77 fn visit_conditional_assignment(&mut self, cursor: &mut TreeCursor) {
78 self.process_children(cursor);
79 }
80
81 fn visit_ternary(&mut self, cursor: &mut TreeCursor) {
82 self.process_children(cursor);
83 }
84
85 fn visit_switch(&mut self, cursor: &mut TreeCursor) {
86 self.process_children(cursor);
87 }
88
89 fn visit_case(&mut self, cursor: &mut TreeCursor) {
90 self.process_children(cursor);
91 }
92
93 fn visit_loop(&mut self, cursor: &mut TreeCursor) {
94 self.process_children(cursor);
95 }
96
97 fn visit_except(&mut self, cursor: &mut TreeCursor) {
98 self.process_children(cursor);
99 }
100
101 fn visit_try_expression(&mut self, cursor: &mut TreeCursor) {
102 self.process_children(cursor);
103 }
104
105 fn visit_jump(&mut self, cursor: &mut TreeCursor) {
106 self.process_children(cursor);
107 }
108
109 fn visit_return(&mut self, cursor: &mut TreeCursor) {
110 self.process_children(cursor);
111 }
112
113 fn visit_binary(&mut self, cursor: &mut TreeCursor) {
114 self.process_children(cursor);
115 }
116
117 fn visit_field(&mut self, cursor: &mut TreeCursor) {
118 self.process_children(cursor);
119 }
120
121 fn visit_call(&mut self, cursor: &mut TreeCursor) {
122 self.process_children(cursor);
123 }
124
125 fn visit_function(&mut self, cursor: &mut TreeCursor) {
126 self.process_children(cursor);
127 }
128
129 fn visit_closure(&mut self, cursor: &mut TreeCursor) {
130 self.process_children(cursor);
131 }
132
133 fn visit_comment(&mut self, cursor: &mut TreeCursor) {
134 self.process_children(cursor);
135 }
136
137 fn visit_string(&mut self, cursor: &mut TreeCursor) {
138 self.process_children(cursor);
139 }
140
141 fn visit_block(&mut self, cursor: &mut TreeCursor) {
142 self.process_children(cursor);
143 }
144
145 fn visit_unknown(&mut self, cursor: &mut TreeCursor) {
146 self.process_children(cursor);
147 }
148
149 fn process_children(&mut self, cursor: &mut TreeCursor) {
150 if cursor.goto_first_child() {
151 loop {
152 self.process_node(cursor);
153
154 if !cursor.goto_next_sibling() {
155 break;
156 }
157 }
158
159 cursor.goto_parent();
160 }
161 }
162
163 fn skip_node(&self, node: &Node) -> bool {
164 !node.is_named()
165 }
166
167 #[allow(clippy::borrowed_box)]
168 fn language(&self) -> &Box<dyn Language + Sync>;
169}