feat(lsp): query by symbol_name; document ast_query match limits

Two ast_query/lsp_query ergonomics improvements that share the tool registration and help files:

- lsp_query accepts symbol_name (+symbol_kind) and resolves the position via AST (resolveLSPSymbolPosition), so callers need not know line:col; line/column are no longer required. SymbolCandidate gains NameLine/NameColumn for the precise identifier position. Ambiguous/unknown names error with candidates / a 'did you mean' hint. Adds TestResolveLSPSymbolPosition.
- ast_query help + tool description now document that matching is keyword/kind-based, not structural: pattern arg/return constraints are not enforced; use name_exact/name_matches/kind_in to filter. Fixes a misleading 'functions returning error' example.
This commit is contained in:
2026-06-20 00:33:32 +01:00
parent b6489ee4bc
commit cc1661d295
5 changed files with 149 additions and 23 deletions
+14 -7
View File
@@ -919,11 +919,15 @@ func kindMatchesNode(kind protocol.SymbolKind, nodeType string) bool {
}
// SymbolCandidate is one symbol matching a name (and optional kind) lookup,
// with its declaration node type and 1-indexed inclusive line range.
// with its declaration node type and 1-indexed inclusive line range. NameLine
// and NameColumn point at the name identifier itself (1-indexed), which is the
// position LSP queries (hover/definition/references) expect.
type SymbolCandidate struct {
NodeType string
StartLine int
EndLine int
NodeType string
StartLine int
EndLine int
NameLine int
NameColumn int
}
// symbolDeclNodeTypes is the set of declaration node types FindSymbolCandidates
@@ -959,10 +963,13 @@ func FindSymbolCandidates(tree *sitter.Tree, content []byte, filename, symbolNam
return true // kind mismatch, keep searching
}
r := NodeRange(n, filename)
nameLoc := NodeLocation(nameNode, filename)
candidates = append(candidates, SymbolCandidate{
NodeType: n.Type(),
StartLine: r.Start.Line,
EndLine: r.End.Line,
NodeType: n.Type(),
StartLine: r.Start.Line,
EndLine: r.End.Line,
NameLine: nameLoc.Line,
NameColumn: nameLoc.Column,
})
return true
})