]> Sergey Matveev's repositories - vim-lsp.git/commitdiff
Add the preliminary support for code lens
authorYegappan Lakshmanan <yegappan@yahoo.com>
Sat, 8 Apr 2023 05:55:31 +0000 (22:55 -0700)
committerYegappan Lakshmanan <yegappan@yahoo.com>
Sat, 8 Apr 2023 05:55:31 +0000 (22:55 -0700)
README.md
autoload/lsp/capabilities.vim
autoload/lsp/codeaction.vim
autoload/lsp/codelens.vim [new file with mode: 0644]
autoload/lsp/lsp.vim
autoload/lsp/lspserver.vim
doc/lsp.txt
plugin/lsp.vim

index ebb1726ea8856a464ef7f541f4dc0b2f1b3a8130..73d382e3b53ef415c55e1a1052f153d7d77b41ef 100644 (file)
--- a/README.md
+++ b/README.md
@@ -157,6 +157,7 @@ The following commands are provided to use the LSP features.
 Command|Description
 -------|-----------
 :LspCodeAction|Apply the code action supplied by the language server to the diagnostic in the current line.
+:LspCodeLens|Display a list of code lens commands and apply a selected code lens command to the current file.
 :LspDiagCurrent|Display the diagnostic message for the current line.
 :LspDiagFirst|Jump to the first diagnostic message for the current buffer.
 :LspDiagHere|Jump to the next diagnostic message in the current line.
index 5fdb1dd0acad642bb84db971cbabc3b7de518dc7..9aefc5389524d041975d879da03bfeb42137fd0e 100644 (file)
@@ -170,6 +170,18 @@ export def ProcessServerCaps(lspserver: dict<any>, caps: dict<any>)
     lspserver.isCodeActionProvider = false
   endif
 
+  # codeLensProvider
+  if lspserver.caps->has_key('codeLensProvider')
+    lspserver.isCodeLensProvider = true
+    if lspserver.caps.codeLensProvider->has_key('resolveProvider')
+      lspserver.isCodeLensResolveProvider = true
+    else
+      lspserver.isCodeLensResolveProvider = false
+    endif
+  else
+    lspserver.isCodeLensProvider = false
+  endif
+
   # workspaceSymbolProvider
   if lspserver.caps->has_key('workspaceSymbolProvider')
     if lspserver.caps.workspaceSymbolProvider->type() == v:t_bool
index 08557671e9fad1772bb14ffd934df654644925de..81a146fe39b9a34499cb008e2a2ca80b70832fd0 100644 (file)
@@ -12,10 +12,14 @@ export def RegisterCmdHandler(cmd: string, Handler: func)
   CommandHandlers[cmd] = Handler
 enddef
 
-def DoCommand(lspserver: dict<any>, cmd: dict<any>)
+export def DoCommand(lspserver: dict<any>, cmd: dict<any>)
   if cmd->has_key('command') && CommandHandlers->has_key(cmd.command)
     var CmdHandler: func = CommandHandlers[cmd.command]
-    call CmdHandler(cmd)
+    try
+      call CmdHandler(cmd)
+    catch
+      util.ErrMsg($'Error: "{cmd.command}" handler raised exception {v:exception}')
+    endtry
   else
     lspserver.executeCommand(cmd)
   endif
diff --git a/autoload/lsp/codelens.vim b/autoload/lsp/codelens.vim
new file mode 100644 (file)
index 0000000..2571665
--- /dev/null
@@ -0,0 +1,32 @@
+vim9script
+
+import './codeaction.vim'
+
+# Functions related to handling LSP code lens
+
+export def ProcessCodeLens(lspserver: dict<any>, codeLensItems: list<dict<any>>)
+  var text: list<string> = []
+  for i in codeLensItems->len()->range()
+    var item = codeLensItems[i]
+    if !item->has_key('command')
+      # resolve the code lens
+      item = lspserver.resolveCodeLens(item)
+      if item->empty()
+       continue
+      endif
+      codeLensItems[i] = item
+    endif
+    text->add(printf("%d. %s\t| L%s:%s", i + 1, item.command.title,
+                       item.range.start.line + 1,
+                       getline(item.range.start.line + 1)))
+  endfor
+
+  var choice = inputlist(['Code Lens:'] + text)
+  if choice < 1 || choice > codeLensItems->len()
+    return
+  endif
+
+  codeaction.DoCommand(lspserver, codeLensItems[choice - 1].command)
+enddef
+
+# vim: tabstop=8 shiftwidth=2 softtabstop=2
index 020c07a3e3487a0de0f5dc315d2867a85b4025a8..7b85dec54e30ccdb2d8c885433c6d8a6bbac9db2 100644 (file)
@@ -795,6 +795,17 @@ export def CodeAction(line1: number, line2: number, query: string)
   lspserver.codeAction(fname, line1, line2, query)
 enddef
 
+# Code lens
+# Uses LSP "textDocument/codeLens" request
+export def CodeLens()
+  var lspserver: dict<any> = buf.CurbufGetServerChecked()
+  if lspserver->empty()
+    return
+  endif
+
+  lspserver.codeLens(@%)
+enddef
+
 # Perform a workspace wide symbol lookup
 # Uses LSP "workspace/symbol" request
 export def SymbolSearch(queryArg: string)
index dbaacea217bc3e56825bef4c72d42b2724bd4d25..8f8ba89ebf0924573893807d54dcc853f83b2a07 100644 (file)
@@ -20,6 +20,7 @@ import './completion.vim'
 import './hover.vim'
 import './signature.vim'
 import './codeaction.vim'
+import './codelens.vim'
 import './callhierarchy.vim' as callhier
 import './typehierarchy.vim' as typehier
 import './inlayhints.vim'
@@ -1165,6 +1166,38 @@ def CodeAction(lspserver: dict<any>, fname_arg: string, line1: number,
   codeaction.ApplyCodeAction(lspserver, reply.result, query)
 enddef
 
+# Request: "textDocument/codeLens"
+# Param: CodeLensParams
+def CodeLens(lspserver: dict<any>, fname: string)
+  # Check whether LSP server supports code lens operation
+  if !lspserver.isCodeLensProvider
+    util.ErrMsg('Error: LSP server does not support code lens operation')
+    return
+  endif
+
+  var params = {textDocument: {uri: util.LspFileToUri(fname)}}
+  var reply = lspserver.rpc('textDocument/codeLens', params)
+  if reply->empty() || reply.result->empty()
+    util.WarnMsg($'Error: No code lens actions found for the current file')
+    return
+  endif
+
+  codelens.ProcessCodeLens(lspserver, reply.result)
+enddef
+
+# Request: "codeLens/resolve"
+# Param: CodeLens
+def ResolveCodeLens(lspserver: dict<any>, codeLens: dict<any>): dict<any>
+  if !lspserver.isCodeLensResolveProvider
+    return {}
+  endif
+  var reply = lspserver.rpc('codeLens/resolve', codeLens)
+  if reply->empty()
+    return {}
+  endif
+  return reply.result
+enddef
+
 # List project-wide symbols matching query string
 # Request: "workspace/symbol"
 # Param: WorkspaceSymbolParams
@@ -1485,6 +1518,8 @@ export def NewLspServer(name_arg: string, path_arg: string, args: list<string>,
     typeHierarchy: function(TypeHiearchy, [lspserver]),
     renameSymbol: function(RenameSymbol, [lspserver]),
     codeAction: function(CodeAction, [lspserver]),
+    codeLens: function(CodeLens, [lspserver]),
+    resolveCodeLens: function(ResolveCodeLens, [lspserver]),
     workspaceQuery: function(WorkspaceQuerySymbols, [lspserver]),
     addWorkspaceFolder: function(AddWorkspaceFolder, [lspserver]),
     removeWorkspaceFolder: function(RemoveWorkspaceFolder, [lspserver]),
index 1aa9086e2bfa9328a1b332fdc66280583929bf00..8f40636d3f93f7b72e97acc913ac1800d6b52391 100644 (file)
@@ -70,6 +70,8 @@ The following commands are provided:
 
 :LspCodeAction         Apply the code action supplied by the language server
                        to the diagnostic in the current line.
+:LspCodeLens           Display all the code lens commands available for the
+                       current file and apply the selected command.
 :LspDiagCurrent                Display the diagnostic message for the current line.
 :LspDiagFirst          Jump to the first diagnostic message for the current
                        buffer.
@@ -477,6 +479,11 @@ can map these commands to keys and make it easier to invoke them.
                        When [query] is not given you will be prompted to select
                        one of the actions supplied by the language server.
 
+                                               *:LspCodeLens*
+:LspCodeLens           Display a list of code lens commands available for the
+                       current buffer and apply the selected code lens
+                       command.
+
                                                *:LspDiagCurrent*
 :LspDiagCurrent                Displays the diagnostic message (if any) for the
                        current line.  If the option 'showDiagInPopup' is set
index 043f75caba2f01ab6e38318f78fee7a26edeb987..46ab79d18f3661ba363660837ab737f1d315b2bb 100644 (file)
@@ -78,6 +78,7 @@ augroup END
 
 # LSP commands
 command! -nargs=? -bar -range LspCodeAction lsp.CodeAction(<line1>, <line2>, <q-args>)
+command! -nargs=0 -bar LspCodeLens lsp.CodeLens()
 command! -nargs=0 -bar -bang LspDiagCurrent lsp.LspShowCurrentDiag(<bang>false)
 command! -nargs=0 -bar LspDiagFirst lsp.JumpToDiag('first')
 command! -nargs=0 -bar LspDiagHighlightDisable lsp.DiagHighlightDisable()
@@ -115,10 +116,10 @@ command! -nargs=0 -bar LspShowServerCapabilities lsp.ShowServerCapabilities()
 command! -nargs=0 -bar LspShowServer lsp.ShowServer()
 command! -nargs=0 -bar LspShowAllServers lsp.ShowAllServers()
 command! -nargs=0 -bar LspShowSignature call LspShowSignature()
-# Clangd specifc extension to switch from one C/C++ source file to a
-# corresponding header file
 command! -nargs=0 -bar LspSubTypeHierarchy lsp.TypeHierarchy(0)
 command! -nargs=0 -bar LspSuperTypeHierarchy lsp.TypeHierarchy(1)
+# Clangd specifc extension to switch from one C/C++ source file to a
+# corresponding header file
 command! -nargs=0 -bar LspSwitchSourceHeader lsp.SwitchSourceHeader()
 command! -nargs=? -bar LspSymbolSearch lsp.SymbolSearch(<q-args>)
 command! -nargs=1 -bar -complete=dir LspWorkspaceAddFolder lsp.AddWorkspaceFolder(<q-args>)