1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
|
local Job = require ('plenary.job')
local List = require('plenary.collections.py_list')
local spinner = require('spinner.core')
local M = {
current_jobs = {}
}
--create a new job and register
--@return ~/.local/share/nvim/site/pack/packer/start/plenary.nvim/lua/plenary/job.lua
function M.jobstart(opts)
opts = opts or {}
-- required options
vim.tbl_extend('force', opts, {
enable_recording = true, -- enable job:result()
})
-- default options
opts.populate_quickfix = opts.populate_quickfix or true
opts.enable_spinner = opts.enable_spinner or true
local title
if opts.format_title then
title = opts.format_title(opts.command, opts.args)
opts.format_title = nil
else
title = opts.command
end
opts.on_exit = vim.schedule_wrap(function(j, code)
if opts.enable_spinner then
spinner.on_progress('end', j.pid, j.pid)
spinner.on_exit(nil, nil, j.pid)
table.remove(M.current_jobs, j.pid)
end
local lines
if code == 0 then
lines = j:result()
else
lines = j:stderr_result()
end
-- strip ansi terminal color codes
for i = 1, #lines do
lines[i] = (lines[i]):gsub(string.char(27) .. '[[0-9;]*m', '')
end
-- only show quickfix if there is output
if opts.populate_quickfix and #lines > 0 then
vim.fn.setqflist({}, 'r', {
title = title,
lines = lines,
efm = '%m',
})
vim.cmd([[doautocmd QuickFixCmdPost]])
end
end)
local j = Job:new(opts)
j:start()
M.current_jobs[j.pid] = j
if opts.enable_spinner then
spinner.on_attach(j.pid, title, vim.fn.bufnr())
spinner.on_progress('begin', j.pid, j.pid)
end
return j
end
function M.make(extra_args)
local makeprg = vim.fn.expandcmd(vim.opt.makeprg:get())
-- split makeprg into command + args
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},
-- strip 'sh -c' from the title (used by progress reporting etc.)
format_title = function(_, args)
return List(args):slice(2,#args):join(' ')
end
}
end
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
|