Skip to content

Commit

Permalink
refactor(neotest): use nio.lsp.Client
Browse files Browse the repository at this point in the history
  • Loading branch information
mrcjkb committed May 23, 2024
1 parent 45075f8 commit ac4409b
Show file tree
Hide file tree
Showing 2 changed files with 44 additions and 56 deletions.
52 changes: 41 additions & 11 deletions lua/rustaceanvim/neotest/init.lua
Original file line number Diff line number Diff line change
Expand Up @@ -63,23 +63,53 @@ end
---@class rustaceanvim.neotest.Position: neotest.Position
---@field runnable? RARunnable

----@param name string
----@return integer
local function find_buffer_by_name(name)
for _, bufnr in ipairs(vim.api.nvim_list_bufs()) do
local buf_name = vim.api.nvim_buf_get_name(bufnr)
if buf_name == name then
return bufnr
end
end
return 0
end

---@package
---@class nio.rustaceanvim.Client: nio.lsp.Client
---@field request nio.rustaceanvim.RequestClient Interface to all requests that can be sent by the client
---@field config vim.lsp.ClientConfig

---@package
---@class nio.rustaceanvim.RequestClient: nio.lsp.RequestClient
---@field experimental_runnables fun(args: nio.lsp.types.ImplementationParams, bufnr: integer?, opts: nio.lsp.RequestOpts): nio.lsp.types.ResponseError|nil, RARunnable[]|nil

---@package
---@param file_path string
---@return neotest.Tree
NeotestAdapter.discover_positions = function(file_path)
---@type rustaceanvim.neotest.Position[]
local positions = {}
local rust_analyzer = require('rustaceanvim.rust_analyzer')
local future = nio.control.future()
rust_analyzer.file_request(file_path, 'experimental/runnables', nil, function(err, runnables)
if err then
future.set_error(err)
else
future.set(runnables)
end
end)
local ok, runnables = pcall(future.wait)
if not ok or type(runnables) ~= 'table' or #runnables == 0 then

local lsp_client = require('rustaceanvim.rust_analyzer').get_client_for_file(file_path, 'experimental/runnables')
if not lsp_client then
---@diagnostic disable-next-line: missing-parameter
return lib.positions.parse_tree(positions)
end
local nio_client = nio.lsp.get_client_by_id(lsp_client.id)
---@cast nio_client nio.rustaceanvim.Client
local bufnr = find_buffer_by_name(file_path)
local params = {
textDocument = {
uri = vim.uri_from_fname(file_path),
},
position = nil,
}
local err, runnables = nio_client.request.experimental_runnables(params, bufnr, {
timeout = 100000,
})

if err or type(runnables) ~= 'table' or #runnables == 0 then
---@diagnostic disable-next-line: missing-parameter
return lib.positions.parse_tree(positions)
end
Expand Down
48 changes: 3 additions & 45 deletions lua/rustaceanvim/rust_analyzer.lua
Original file line number Diff line number Diff line change
Expand Up @@ -54,56 +54,14 @@ M.buf_request = function(bufnr, method, params, handler)
return client_found
end

----@param name string
----@return integer
local function find_buffer_by_name(name)
for _, bufnr in ipairs(vim.api.nvim_list_bufs()) do
local buf_name = vim.api.nvim_buf_get_name(bufnr)
if buf_name == name then
return bufnr
end
end
return 0
end

---@param file_path string Search for clients with a root_dir matching this file path
---@param method string LSP method name
---@param params table|nil Parameters to send to the server
---@param handler? lsp.Handler See |lsp-handler|
--- If nil, follows resolution strategy defined in |lsp-handler-configuration|
M.file_request = function(file_path, method, params, handler)
local client_found = false
---@return lsp.Client|nil
M.get_client_for_file = function(file_path, method)
for _, client in ipairs(M.get_active_rustaceanvim_clients(nil, { method = method })) do
local root_dir = client.config.root_dir
if root_dir and vim.startswith(os.normalize_path_on_windows(file_path), root_dir) then
local bufnr = find_buffer_by_name(file_path)
if not params then
params = {
textDocument = {
uri = vim.uri_from_fname(file_path),
},
position = nil,
}
end
client.request(method, params, handler, bufnr)
client_found = true
if bufnr == -1 then
return
end
end
end
if not client_found then
local error_msg = 'No rust-analyzer client for ' .. method .. ' and file ' .. file_path
if handler then
---@type lsp.HandlerContext
local ctx = {
bufnr = -1,
client_id = -1,
method = method,
}
handler({ code = -1, message = error_msg }, nil, ctx)
else
vim.notify(error_msg, vim.log.levels.ERROR)
return client
end
end
end
Expand Down

0 comments on commit ac4409b

Please sign in to comment.