mirror of
https://github.com/neovim/neovim.git
synced 2025-10-26 12:27:24 +00:00
fix(lsp): deduplicate completion items #36166
The current implementation has a race condition where items are appended to the completion list twice when a second completion runs while the first is still going. This hotfix just deduplicates the entire list. Co-authored-by: Tomasz N <przepompownia@users.noreply.github.com>
This commit is contained in:
@@ -482,10 +482,7 @@ local function trigger(bufnr, clients, ctx)
|
||||
end
|
||||
|
||||
local win = api.nvim_get_current_win()
|
||||
local cursor_row, cursor_col = unpack(api.nvim_win_get_cursor(win)) --- @type integer, integer
|
||||
local line = api.nvim_get_current_line()
|
||||
local line_to_cursor = line:sub(1, cursor_col)
|
||||
local word_boundary = vim.fn.match(line_to_cursor, '\\k*$')
|
||||
local cursor_row = api.nvim_win_get_cursor(win)[1]
|
||||
local start_time = vim.uv.hrtime() --[[@as integer]]
|
||||
Context.last_request_time = start_time
|
||||
|
||||
@@ -496,13 +493,19 @@ local function trigger(bufnr, clients, ctx)
|
||||
Context.pending_requests = {}
|
||||
Context.isIncomplete = false
|
||||
|
||||
local row_changed = api.nvim_win_get_cursor(win)[1] ~= cursor_row
|
||||
local new_cursor_row, cursor_col = unpack(api.nvim_win_get_cursor(win)) --- @type integer, integer
|
||||
local row_changed = new_cursor_row ~= cursor_row
|
||||
local mode = api.nvim_get_mode().mode
|
||||
if row_changed or not (mode == 'i' or mode == 'ic') then
|
||||
return
|
||||
end
|
||||
|
||||
local matches --[[@type table]] = vim.fn.complete_info({ 'items' })['items']
|
||||
local line = api.nvim_get_current_line()
|
||||
local line_to_cursor = line:sub(1, cursor_col)
|
||||
local word_boundary = vim.fn.match(line_to_cursor, '\\k*$')
|
||||
|
||||
local matches = {}
|
||||
|
||||
local server_start_boundary --- @type integer?
|
||||
for client_id, response in pairs(responses) do
|
||||
local client = lsp.get_client_by_id(client_id)
|
||||
@@ -530,9 +533,25 @@ local function trigger(bufnr, clients, ctx)
|
||||
result,
|
||||
encoding
|
||||
)
|
||||
|
||||
vim.list_extend(matches, client_matches)
|
||||
end
|
||||
end
|
||||
|
||||
--- @type table[]
|
||||
local prev_matches = vim.fn.complete_info({ 'items', 'matches' })['items']
|
||||
|
||||
--- @param prev_match table
|
||||
prev_matches = vim.tbl_filter(function(prev_match)
|
||||
local client_id = vim.tbl_get(prev_match, 'user_data', 'nvim', 'lsp', 'client_id')
|
||||
if client_id and responses[client_id] ~= nil then
|
||||
return false
|
||||
end
|
||||
return vim.tbl_get(prev_match, 'match')
|
||||
end, prev_matches)
|
||||
|
||||
matches = vim.list_extend(prev_matches, matches)
|
||||
|
||||
local start_col = (server_start_boundary or word_boundary) + 1
|
||||
Context.cursor = { cursor_row, start_col }
|
||||
vim.fn.complete(start_col, matches)
|
||||
|
||||
Reference in New Issue
Block a user