diff options
| author | Robert Günzler <r@gnzler.io> | 2021-08-02 13:55:25 +0200 |
|---|---|---|
| committer | Robert Günzler <r@gnzler.io> | 2021-08-02 13:55:25 +0200 |
| commit | b22dc38564dcc8903f501ed92843aa9db9fd44a7 (patch) | |
| tree | 60820b77a81a6c96ca7a86e82fa4727c30c5247f /.vim/lua/job.lua | |
| parent | a640482e61fa6afcbdb6e974ef9b0bb956a9649c (diff) | |
vim: use plenary for jobs
Diffstat (limited to '')
| -rw-r--r-- | .vim/lua/job.lua | 129 |
1 files changed, 98 insertions, 31 deletions
diff --git a/.vim/lua/job.lua b/.vim/lua/job.lua index a3591e5..7261d24 100644 --- a/.vim/lua/job.lua +++ b/.vim/lua/job.lua @@ -1,45 +1,112 @@ +local Job = require ('plenary.job') +local List = require('plenary.collections.py_list') +local spinner = require('spinner.core') -local M = {} +local M = { + current_jobs = {} +} -function M.jobstart(cmd) - local output = {} +function M.jobstart(opts, _wrap_command_for_presentation) + local opts = opts or {} - local function on_event(job_id, data, event) - if event == 'stdout' or event == 'stderr' then - if data then - vim.list_extend(output, data) - end + if opts.format_title then + title = opts.format_title(opts.command, opts.args) + opts.format_title = nil + else + title = opts.command + end + + opts.enable_recording = true -- enable job:result() + + opts.on_exit = vim.schedule_wrap(function(j, retval) + spinner.on_progress('end', j.pid, j.pid) + spinner.on_exit(nil, nil, j.pid) + + local lines = j:result() + if not lines or #lines < 1 then + lines = j:stderr_result() end - if event == 'exit' then - vim.fn.setqflist({}, ' ', { - title = cmd, - lines = output, - }) + vim.fn.setqflist({}, ' ', { + title = title, + lines = lines, + }) + if #lines > 0 then vim.api.nvim_command('doautocmd QuickFixCmdPost') end - end - local job_id = require('spinner.job').jobstart(cmd, { - on_stdout = on_event, - on_stderr = on_event, - on_exit = on_event, - stdout_buffered = true, - stderr_buffered = true, - }) - return job_id + for k, v in ipairs(M.current_jobs) do + if v.pid == j.pid then + table.remove(M.current_jobs, k) + break + end + end + end) + + local j = Job:new(opts) + j:start() + table.insert(M.current_jobs, j) + + spinner.on_attach(j.pid, title, vim.fn.bufnr()) + spinner.on_progress('begin', j.pid, j.pid) + + return j end -function M.make(args) - local args = args or {} - local makeprg = vim.opt.makeprg:get() - local cmd = vim.split(vim.fn.expandcmd(makeprg), ' ') - table.foreach(args, function(_, v) table.insert(cmd, v) end) - return M.jobstart(cmd) +function M.make(extra_args) + local makeprg = vim.fn.expandcmd(vim.opt.makeprg:get()) + local args = vim.split(makeprg, ' ') + local command = args[1] + table.remove(args, 1) + + local extra_args = extra_args or {} + table.foreach(extra_args, function(_, v) table.insert(args, v) end) + + return M.jobstart { + command = command, + args = args, + } +end + +function M.sh(command_string) + return M.jobstart { + command = vim.env.SHELL, + args = {'-c', command_string}, + + format_title = function(_, args) + return List(args):slice(2,#args):join(' ') + end + } end -function M.sh(cmd) - local cmd = {vim.env.SHELL, '-c', cmd} - return M.jobstart(cmd) + +function M.gen_entry_from_job() + return function(entry) + return { + value = entry, + ordinal = entry.pid, + display = entry.command .. ' ' .. table.concat(entry.args, ' '), + } + end +end + +function M.cancel_job() + if #M.current_jobs < 1 then return end + require('telescope.pickers').new({}, { + prompt_title = 'Jobs', + finder = require('telescope.finders').new_table { + results = M.current_jobs, + entry_maker = M.gen_entry_from_job(), + }, + sorter = require('telescope.sorters').fuzzy_with_index_bias(), + attach_mappings = function(bufnr) + require('telescope.actions.set').select:replace(function(bufnr, type) + local entry = require('telescope.actions.state').get_selected_entry() + require('telescope.actions').close(bufnr) + entry.value:shutdown(1, 'SIGKILL') + end) + return true + end + }):find() end return M |