diff options
Diffstat (limited to 'test/functional/plugin/lsp_spec.lua')
-rw-r--r-- | test/functional/plugin/lsp_spec.lua | 175 |
1 files changed, 150 insertions, 25 deletions
diff --git a/test/functional/plugin/lsp_spec.lua b/test/functional/plugin/lsp_spec.lua index 6d3af115fa..2b7198bf63 100644 --- a/test/functional/plugin/lsp_spec.lua +++ b/test/functional/plugin/lsp_spec.lua @@ -29,6 +29,16 @@ teardown(function() os.remove(fake_lsp_logfile) end) +local function clear_notrace() + -- problem: here be dragons + -- solution: don't look for dragons to closely + clear {env={ + NVIM_LUA_NOTRACK="1"; + VIMRUNTIME=os.getenv"VIMRUNTIME"; + }} +end + + local function fake_lsp_server_setup(test_name, timeout_ms, options) exec_lua([=[ lsp = require('vim.lsp') @@ -36,6 +46,7 @@ local function fake_lsp_server_setup(test_name, timeout_ms, options) TEST_RPC_CLIENT_ID = lsp.start_client { cmd_env = { NVIM_LOG_FILE = logfile; + NVIM_LUA_NOTRACK = "1"; }; cmd = { vim.v.progpath, '-Es', '-u', 'NONE', '--headless', @@ -65,7 +76,7 @@ end local function test_rpc_server(config) if config.test_name then - clear() + clear_notrace() fake_lsp_server_setup(config.test_name, config.timeout_ms or 1e3, config.options) end local client = setmetatable({}, { @@ -120,7 +131,7 @@ end describe('LSP', function() describe('server_name specified', function() before_each(function() - clear() + clear_notrace() -- Run an instance of nvim on the file which contains our "scripts". -- Pass TEST_NAME to pick the script. local test_name = "basic_init" @@ -250,6 +261,10 @@ describe('LSP', function() end) it('should succeed with manual shutdown', function() + if 'openbsd' == helpers.uname() then + pending('hangs the build on openbsd #14028, re-enable with freeze timeout #14204') + return + end local expected_callbacks = { {NIL, "shutdown", {}, 1, NIL}; {NIL, "test", {}, 1}; @@ -314,7 +329,7 @@ describe('LSP', function() } end) it('workspace/configuration returns NIL per section if client was started without config.settings', function() - clear() + clear_notrace() fake_lsp_server_setup('workspace/configuration no settings') eq({ NIL, NIL, }, exec_lua [[ local params = { @@ -941,7 +956,7 @@ end) describe('LSP', function() before_each(function() - clear() + clear_notrace() end) local function make_edit(y_0, x_0, y_1, x_1, text) @@ -1109,14 +1124,14 @@ describe('LSP', function() '2nd line of 语text'; }, buf_lines(target_bufnr)) end) - it('correctly goes ahead with the edit if the version is vim.NIL', function() - -- we get vim.NIL when we decode json null value. - local json = exec_lua[[ - return vim.fn.json_decode("{ \"a\": 1, \"b\": null }") - ]] - eq(json.b, exec_lua("return vim.NIL")) - - exec_lua('vim.lsp.util.apply_text_document_edit(...)', text_document_edit(exec_lua("return vim.NIL"))) + it('always accepts edit with version = 0', function() + exec_lua([[ + local args = {...} + local bufnr = select(1, ...) + local text_edit = select(2, ...) + vim.lsp.util.buf_versions[bufnr] = 10 + vim.lsp.util.apply_text_document_edit(text_edit) + ]], target_bufnr, text_document_edit(0)) eq({ 'First ↥ 🤦 🦄 line of text'; '2nd line of 语text'; @@ -1805,20 +1820,36 @@ describe('LSP', function() end) describe('lsp.util.jump_to_location', function() - local target_bufnr + local default_target_bufnr + local default_target_uri = 'file://fake/uri' - before_each(function() - target_bufnr = exec_lua [[ - local bufnr = vim.uri_to_bufnr("file://fake/uri") - local lines = {"1st line of text", "å å ɧ 汉语 ↥ 🤦 🦄"} + local create_buf = function(uri, lines) + for i, line in ipairs(lines) do + lines[i] = '"' .. line .. '"' + end + lines = table.concat(lines, ", ") + + -- Let's set "hidden" to true in order to avoid errors when switching + -- between buffers in test. + local code = string.format([[ + vim.api.nvim_set_option('hidden', true) + + local bufnr = vim.uri_to_bufnr("%s") + local lines = {%s} vim.api.nvim_buf_set_lines(bufnr, 0, 1, false, lines) return bufnr - ]] + ]], uri, lines) + + return exec_lua(code) + end + + before_each(function() + default_target_bufnr = create_buf(default_target_uri, {'1st line of text', 'å å ɧ 汉语 ↥ 🤦 🦄'}) end) - local location = function(start_line, start_char, end_line, end_char) + local location = function(uri, start_line, start_char, end_line, end_char) return { - uri = "file://fake/uri", + uri = uri, range = { start = { line = start_line, character = start_char }, ["end"] = { line = end_line, character = end_char }, @@ -1826,9 +1857,9 @@ describe('LSP', function() } end - local jump = function(msg) + local jump = function(bufnr, msg) eq(true, exec_lua('return vim.lsp.util.jump_to_location(...)', msg)) - eq(target_bufnr, exec_lua[[return vim.fn.bufnr('%')]]) + eq(bufnr, exec_lua[[return vim.fn.bufnr('%')]]) return { line = exec_lua[[return vim.fn.line('.')]], col = exec_lua[[return vim.fn.col('.')]], @@ -1836,13 +1867,13 @@ describe('LSP', function() end it('jumps to a Location', function() - local pos = jump(location(0, 9, 0, 9)) + local pos = jump(default_target_bufnr, location(default_target_uri, 0, 9, 0, 9)) eq(1, pos.line) eq(10, pos.col) end) it('jumps to a LocationLink', function() - local pos = jump({ + local pos = jump(default_target_bufnr, { targetUri = "file://fake/uri", targetSelectionRange = { start = { line = 0, character = 4 }, @@ -1858,11 +1889,105 @@ describe('LSP', function() end) it('jumps to the correct multibyte column', function() - local pos = jump(location(1, 2, 1, 2)) + local pos = jump(default_target_bufnr, location(default_target_uri, 1, 2, 1, 2)) eq(2, pos.line) eq(4, pos.col) eq('å', exec_lua[[return vim.fn.expand('<cword>')]]) end) + + it('adds current position to jumplist before jumping', function() + exec_lua([[ + vim.api.nvim_win_set_buf(0, ...) + vim.api.nvim_win_set_cursor(0, {2, 0}) + ]], default_target_bufnr) + jump(default_target_bufnr, location(default_target_uri, 0, 9, 0, 9)) + + local mark = exec_lua([[return vim.inspect(vim.api.nvim_buf_get_mark(..., "'"))]], default_target_bufnr) + eq('{ 2, 0 }', mark) + end) + + it('should not push item to tagstack if destination is the same as source', function() + -- Set cursor at the 2nd line, 1st character. This is the source position + -- for the test, and will also be the destination one, making the cursor + -- "motionless", thus not triggering a push to the tagstack. + exec_lua(string.format([[ + vim.api.nvim_win_set_buf(0, %d) + vim.api.nvim_win_set_cursor(0, {2, 0}) + ]], default_target_bufnr)) + + -- Jump to 'f' in 'foobar', at the 2nd line. + jump(default_target_bufnr, location(default_target_uri, 1, 0, 1, 0)) + + local stack = exec_lua[[return vim.fn.gettagstack()]] + eq(0, stack.length) + end) + + it('should not push the same item from same buffer twice to tagstack', function() + -- Set cursor at the 2nd line, 5th character. + exec_lua(string.format([[ + vim.api.nvim_win_set_buf(0, %d) + vim.api.nvim_win_set_cursor(0, {2, 4}) + ]], default_target_bufnr)) + + local stack + + -- Jump to 1st line, 1st column. + jump(default_target_bufnr, location(default_target_uri, 0, 0, 0, 0)) + + stack = exec_lua[[return vim.fn.gettagstack()]] + eq({default_target_bufnr, 2, 5, 0}, stack.items[1].from) + + -- Go back to 5th character at 2nd line, which is currently at the top of + -- the tagstack. + exec_lua(string.format([[ + vim.api.nvim_win_set_cursor(0, {2, 4}) + ]], default_target_bufnr)) + + -- Jump again to 1st line, 1st column. Since we're jumping from the same + -- position we have just jumped from, this jump shouldn't be pushed to + -- the tagstack. + jump(default_target_bufnr, location(default_target_uri, 0, 0, 0, 0)) + + stack = exec_lua[[return vim.fn.gettagstack()]] + eq({default_target_bufnr, 2, 5, 0}, stack.items[1].from) + eq(1, stack.length) + end) + + it('should not push the same item from another buffer twice to tagstack', function() + local target_uri = 'file://foo/bar' + local target_bufnr = create_buf(target_uri, {'this is a line', 'foobar'}) + + -- Set cursor at the 1st line, 3rd character of the default test buffer. + exec_lua(string.format([[ + vim.api.nvim_win_set_buf(0, %d) + vim.api.nvim_win_set_cursor(0, {1, 2}) + ]], default_target_bufnr)) + + local stack + + -- Jump to 1st line, 1st column of a different buffer from the source + -- position. + jump(target_bufnr, location(target_uri, 0, 0, 0, 0)) + + stack = exec_lua[[return vim.fn.gettagstack()]] + eq({default_target_bufnr, 1, 3, 0}, stack.items[1].from) + + -- Go back to 3rd character at 1st line of the default test buffer, which + -- is currently at the top of the tagstack. + exec_lua(string.format([[ + vim.api.nvim_win_set_buf(0, %d) + vim.api.nvim_win_set_cursor(0, {1, 2}) + ]], default_target_bufnr)) + + -- Jump again to 1st line, 1st column of the different buffer. Since + -- we're jumping from the same position we have just jumped from, this + -- jump shouldn't be pushed to the tagstack. + jump(target_bufnr, location(target_uri, 0, 0, 0, 0)) + + stack = exec_lua[[return vim.fn.gettagstack()]] + eq({default_target_bufnr, 1, 3, 0}, stack.items[1].from) + eq(1, stack.length) + end) end) describe('lsp.util._make_floating_popup_size', function() |