aboutsummaryrefslogtreecommitdiffstats
path: root/lua
diff options
context:
space:
mode:
authorDavid Lukes <dafydd.lukes@gmail.com>2020-04-28 05:48:35 +0200
committerGitHub <noreply@github.com>2020-04-27 20:48:35 -0700
commit9a8e3543eed294099002413d1b9b99227719bbbf (patch)
tree3b5f4c56aaf79ab0dc21289a75ca6f29ebd1f53f /lua
parent[docgen] Update README.md (diff)
downloadnvim-lspconfig-9a8e3543eed294099002413d1b9b99227719bbbf.tar
nvim-lspconfig-9a8e3543eed294099002413d1b9b99227719bbbf.tar.gz
nvim-lspconfig-9a8e3543eed294099002413d1b9b99227719bbbf.tar.bz2
nvim-lspconfig-9a8e3543eed294099002413d1b9b99227719bbbf.tar.lz
nvim-lspconfig-9a8e3543eed294099002413d1b9b99227719bbbf.tar.xz
nvim-lspconfig-9a8e3543eed294099002413d1b9b99227719bbbf.tar.zst
nvim-lspconfig-9a8e3543eed294099002413d1b9b99227719bbbf.zip
Use builtin terminal for util.sh output (#208)
close https://github.com/neovim/nvim-lsp/issues/207 close https://github.com/neovim/nvim-lsp/pull/201 Using `termopen()`, `util.sh` gets full terminal functionality for free: - progress bars leveraging `\r` and other more fancy output types (e.g. curses UIs) - interactive prompts - canceling with `Ctrl-C` - etc. The drawback is that currently (see https://github.com/neovim/neovim/issues/7607), the `on_exit` callback for `termopen()`/`jobstart()` *has* to be a VimL function, which means a global VimL function has to be created on-the-fly with a name which hopefully won't clobber anything that's already defined. Like #201, this commit makes sure that the output buffer remains open if the script exits with anything else than 0.
Diffstat (limited to 'lua')
-rw-r--r--lua/nvim_lsp/util.lua67
1 files changed, 19 insertions, 48 deletions
diff --git a/lua/nvim_lsp/util.lua b/lua/nvim_lsp/util.lua
index 11d3473d..c40c801d 100644
--- a/lua/nvim_lsp/util.lua
+++ b/lua/nvim_lsp/util.lua
@@ -409,58 +409,29 @@ function M.npm_installer(config)
end
function M.sh(script, cwd)
- api.nvim_command("10new")
assert(cwd and M.path.is_dir(cwd), "sh: Invalid directory")
- local winnr = api.nvim_get_current_win()
+ -- switching to insert mode makes the buffer scroll as new output is added
+ -- and makes it easy and intuitive to cancel the operation with Ctrl-C
+ api.nvim_command("10new | startinsert")
local bufnr = api.nvim_get_current_buf()
- local stdin = uv.new_pipe(false)
- local stdout = uv.new_pipe(false)
- local stderr = uv.new_pipe(false)
- -- luacheck: no unused
- local handle, pid
- handle, pid = uv.spawn("sh", {
- stdio = {stdin, stdout, stderr};
- cwd = cwd;
- }, function()
- stdin:close()
- stdout:close()
- stderr:close()
- handle:close()
- vim.schedule(function()
- api.nvim_command("silent bwipeout! "..bufnr)
- end)
- end)
-
- -- If the buffer closes, then kill our process.
- api.nvim_buf_attach(bufnr, false, {
- on_detach = function()
- if not handle:is_closing() then
- handle:kill(15)
- end
- end;
- })
+ -- TODO: The on_exit callback needs to be a VimL function, so here's a quick
+ -- and dirty way of creating one with a hopefully unique name, so that
+ -- different runs of M.sh don't stomp on each other's callbacks (or some
+ -- other VimL functions for that matter). If it ever becomes possible to pass
+ -- Lua callbacks to termopen/jobstart, switch to a local Lua function closing
+ -- over bufnr as a much cleaner alternative.
+ -- See https://github.com/neovim/neovim/issues/7607
+ local viml_on_exit = "Nvim_lspUtilShOn_exit"..bufnr
+ api.nvim_command([[
+ function! ]]..viml_on_exit..[[(job_id, code, event_type)
+ if !a:code
+ silent bwipeout! ]]..bufnr..[[|
+ endif
+ endfunction
+ ]])
- local output_buf = ''
- local function update_chunk(err, chunk)
- if chunk then
- output_buf = output_buf..chunk
- local lines = vim.split(output_buf, '\n', true)
- api.nvim_buf_set_option(bufnr, "modifiable", true)
- api.nvim_buf_set_lines(bufnr, 0, -1, false, lines)
- api.nvim_buf_set_option(bufnr, "modifiable", false)
- api.nvim_buf_set_option(bufnr, "modified", false)
- if api.nvim_win_is_valid(winnr) then
- api.nvim_win_set_cursor(winnr, {#lines, 0})
- end
- end
- end
- update_chunk = vim.schedule_wrap(update_chunk)
- stdout:read_start(update_chunk)
- stderr:read_start(update_chunk)
- stdin:write(script)
- stdin:write("\n")
- stdin:shutdown()
+ fn.termopen({"sh", "-c", script}, {cwd = cwd, on_exit = viml_on_exit})
end
function M.format_vspackage_url(extension_name)