MCPcopy Create free account
hub / github.com/PHPantom-dev/phpantom_lsp / find_enclosing_context

Function find_enclosing_context

src/code_actions/extract_function.rs:155–238  ·  view source on GitHub ↗

Determine the extraction target and insertion point by walking the AST.

(content: &str, offset: u32, uses_this: bool)

Source from the content-addressed store, hash-verified

153
154/// Determine the extraction target and insertion point by walking the AST.
155fn find_enclosing_context(content: &str, offset: u32, uses_this: bool) -> Option<EnclosingContext> {
156 let arena = Bump::new();
157 let file_id = mago_database::file::FileId::new("extract_fn_ctx");
158 let program = mago_syntax::parser::parse_file_content(&arena, file_id, content);
159
160 let ctx = find_cursor_context(&program.statements, offset);
161
162 match ctx {
163 CursorContext::InClassLike {
164 member,
165 all_members,
166 ..
167 } => {
168 if let MemberContext::Method(method, true) = member {
169 let is_static = method.modifiers.iter().any(|m| m.is_static());
170 let enclosing_name = method.name.value.to_string();
171
172 // Collect sibling method names for scoped deduplication.
173 let sibling_method_names: Vec<String> = all_members
174 .iter()
175 .filter_map(|m| {
176 if let ClassLikeMember::Method(m) = m {
177 Some(m.name.value.to_string())
178 } else {
179 None
180 }
181 })
182 .collect();
183
184 // For method extraction, insert before the closing `}` of the class.
185 // Find the class closing brace by walking up from the method.
186 let class_end = find_class_end_offset(&program.statements, offset);
187
188 if let MethodBody::Concrete(block) = &method.body {
189 let body_start = block.left_brace.start.offset as usize;
190
191 if uses_this && is_static {
192 // $this in a static method — can't extract as method.
193 // Fall back to extracting as a function.
194 let func_end = block.right_brace.end.offset as usize;
195 return Some(EnclosingContext {
196 target: ExtractionTarget::Function,
197 insert_offset: find_after_class_end(&program.statements, offset)
198 .unwrap_or(func_end),
199 body_start,
200 is_static,
201 enclosing_name,
202 sibling_method_names: Vec::new(),
203 });
204 }
205
206 return Some(EnclosingContext {
207 target: ExtractionTarget::Method,
208 insert_offset: class_end.unwrap_or(block.right_brace.end.offset as usize),
209 body_start,
210 is_static,
211 enclosing_name,
212 sibling_method_names,

Callers 4

detects_function_contextFunction · 0.85
detects_method_contextFunction · 0.85

Calls 5

find_cursor_contextFunction · 0.85
find_class_end_offsetFunction · 0.85
find_after_class_endFunction · 0.85
iterMethod · 0.80
find_line_endFunction · 0.70

Tested by 3

detects_function_contextFunction · 0.68
detects_method_contextFunction · 0.68