1package lsp
2
3import "github.com/charmbracelet/crush/internal/lsp/protocol"
4
5func (c *Client) setCapabilities(caps protocol.ServerCapabilities) {
6 c.capsMu.Lock()
7 defer c.capsMu.Unlock()
8 c.caps = caps
9 c.capsSet.Store(true)
10}
11
12func (c *Client) getCapabilities() (protocol.ServerCapabilities, bool) {
13 c.capsMu.RLock()
14 defer c.capsMu.RUnlock()
15 return c.caps, c.capsSet.Load()
16}
17
18func (c *Client) IsMethodSupported(method string) bool {
19 // Always allow core lifecycle and generic methods
20 switch method {
21 case "initialize", "shutdown", "exit", "$/cancelRequest":
22 return true
23 }
24
25 caps, ok := c.getCapabilities()
26 if !ok {
27 // caps not set yet, be permissive
28 return true
29 }
30
31 switch method {
32 case "textDocument/hover":
33 return caps.HoverProvider != nil
34 case "textDocument/definition":
35 return caps.DefinitionProvider != nil
36 case "textDocument/references":
37 return caps.ReferencesProvider != nil
38 case "textDocument/implementation":
39 return caps.ImplementationProvider != nil
40 case "textDocument/typeDefinition":
41 return caps.TypeDefinitionProvider != nil
42 case "textDocument/documentColor", "textDocument/colorPresentation":
43 return caps.ColorProvider != nil
44 case "textDocument/foldingRange":
45 return caps.FoldingRangeProvider != nil
46 case "textDocument/declaration":
47 return caps.DeclarationProvider != nil
48 case "textDocument/selectionRange":
49 return caps.SelectionRangeProvider != nil
50 case "textDocument/prepareCallHierarchy", "callHierarchy/incomingCalls", "callHierarchy/outgoingCalls":
51 return caps.CallHierarchyProvider != nil
52 case "textDocument/semanticTokens/full", "textDocument/semanticTokens/full/delta", "textDocument/semanticTokens/range":
53 return caps.SemanticTokensProvider != nil
54 case "textDocument/linkedEditingRange":
55 return caps.LinkedEditingRangeProvider != nil
56 case "workspace/willCreateFiles":
57 return caps.Workspace != nil && caps.Workspace.FileOperations != nil && caps.Workspace.FileOperations.WillCreate != nil
58 case "workspace/willRenameFiles":
59 return caps.Workspace != nil && caps.Workspace.FileOperations != nil && caps.Workspace.FileOperations.WillRename != nil
60 case "workspace/willDeleteFiles":
61 return caps.Workspace != nil && caps.Workspace.FileOperations != nil && caps.Workspace.FileOperations.WillDelete != nil
62 case "textDocument/moniker":
63 return caps.MonikerProvider != nil
64 case "textDocument/prepareTypeHierarchy", "typeHierarchy/supertypes", "typeHierarchy/subtypes":
65 return caps.TypeHierarchyProvider != nil
66 case "textDocument/inlineValue":
67 return caps.InlineValueProvider != nil
68 case "textDocument/inlayHint", "inlayHint/resolve":
69 return caps.InlayHintProvider != nil
70 case "textDocument/diagnostic", "workspace/diagnostic":
71 return caps.DiagnosticProvider != nil
72 case "textDocument/inlineCompletion":
73 return caps.InlineCompletionProvider != nil
74 case "workspace/textDocumentContent":
75 return caps.Workspace != nil && caps.Workspace.TextDocumentContent != nil
76 case "textDocument/willSaveWaitUntil":
77 if caps.TextDocumentSync == nil {
78 return false
79 }
80 return true
81 case "textDocument/completion", "completionItem/resolve":
82 return caps.CompletionProvider != nil
83 case "textDocument/signatureHelp":
84 return caps.SignatureHelpProvider != nil
85 case "textDocument/documentHighlight":
86 return caps.DocumentHighlightProvider != nil
87 case "textDocument/documentSymbol":
88 return caps.DocumentSymbolProvider != nil
89 case "textDocument/codeAction", "codeAction/resolve":
90 return caps.CodeActionProvider != nil
91 case "workspace/symbol", "workspaceSymbol/resolve":
92 return caps.WorkspaceSymbolProvider != nil
93 case "textDocument/codeLens", "codeLens/resolve":
94 return caps.CodeLensProvider != nil
95 case "textDocument/documentLink", "documentLink/resolve":
96 return caps.DocumentLinkProvider != nil
97 case "textDocument/formatting":
98 return caps.DocumentFormattingProvider != nil
99 case "textDocument/rangeFormatting":
100 return caps.DocumentRangeFormattingProvider != nil
101 case "textDocument/rangesFormatting":
102 return caps.DocumentRangeFormattingProvider != nil
103 case "textDocument/onTypeFormatting":
104 return caps.DocumentOnTypeFormattingProvider != nil
105 case "textDocument/rename", "textDocument/prepareRename":
106 return caps.RenameProvider != nil
107 case "workspace/executeCommand":
108 return caps.ExecuteCommandProvider != nil
109 default:
110 return true
111 }
112}