feat(#1974): experimental.git.async see https://github.com/nvim-tree/nvim-tree.lua/issues/2104 (#2094)
* async git watcher reload; callback hell for now * async git watcher reload; revert unnecessary extractions * async git watcher reload; callback and non-callback functions are required for sync codepaths that loop * async git watcher reload * async git watcher reload * feat(#1974): experimental.git.async * feat(#1974): experimental.git.async
This commit is contained in:
committed by
GitHub
parent
7ad1c204c4
commit
0ef3d4613f
@@ -69,7 +69,7 @@ function Runner:_log_raw_output(output)
|
||||
end
|
||||
end
|
||||
|
||||
function Runner:_run_git_job()
|
||||
function Runner:_run_git_job(callback)
|
||||
local handle, pid
|
||||
local stdout = vim.loop.new_pipe(false)
|
||||
local stderr = vim.loop.new_pipe(false)
|
||||
@@ -78,6 +78,9 @@ function Runner:_run_git_job()
|
||||
local function on_finish(rc)
|
||||
self.rc = rc or 0
|
||||
if timer:is_closing() or stdout:is_closing() or stderr:is_closing() or (handle and handle:is_closing()) then
|
||||
if callback then
|
||||
callback()
|
||||
end
|
||||
return
|
||||
end
|
||||
timer:stop()
|
||||
@@ -91,6 +94,10 @@ function Runner:_run_git_job()
|
||||
end
|
||||
|
||||
pcall(vim.loop.kill, pid)
|
||||
|
||||
if callback then
|
||||
callback()
|
||||
end
|
||||
end
|
||||
|
||||
local opts = self:_getopts(stdout, stderr)
|
||||
@@ -142,25 +149,7 @@ function Runner:_wait()
|
||||
end
|
||||
end
|
||||
|
||||
-- This module runs a git process, which will be killed if it takes more than timeout which defaults to 400ms
|
||||
function Runner.run(opts)
|
||||
local profile = log.profile_start("git job %s %s", opts.project_root, opts.path)
|
||||
|
||||
local self = setmetatable({
|
||||
project_root = opts.project_root,
|
||||
path = opts.path,
|
||||
list_untracked = opts.list_untracked,
|
||||
list_ignored = opts.list_ignored,
|
||||
timeout = opts.timeout or 400,
|
||||
output = {},
|
||||
rc = nil, -- -1 indicates timeout
|
||||
}, Runner)
|
||||
|
||||
self:_run_git_job()
|
||||
self:_wait()
|
||||
|
||||
log.profile_end(profile)
|
||||
|
||||
function Runner:_finalise(opts)
|
||||
if self.rc == -1 then
|
||||
log.line("git", "job timed out %s %s", opts.project_root, opts.path)
|
||||
timeouts = timeouts + 1
|
||||
@@ -179,8 +168,55 @@ function Runner.run(opts)
|
||||
else
|
||||
log.line("git", "job success %s %s", opts.project_root, opts.path)
|
||||
end
|
||||
end
|
||||
|
||||
return self.output
|
||||
--- Runs a git process, which will be killed if it takes more than timeout which defaults to 400ms
|
||||
--- @param opts table
|
||||
--- @param callback function|nil executed passing return when complete
|
||||
--- @return table|nil status by absolute path, nil if callback present
|
||||
function Runner.run(opts, callback)
|
||||
local self = setmetatable({
|
||||
project_root = opts.project_root,
|
||||
path = opts.path,
|
||||
list_untracked = opts.list_untracked,
|
||||
list_ignored = opts.list_ignored,
|
||||
timeout = opts.timeout or 400,
|
||||
output = {},
|
||||
rc = nil, -- -1 indicates timeout
|
||||
}, Runner)
|
||||
|
||||
local async = callback ~= nil and self.config.git_async
|
||||
local profile = log.profile_start("git %s job %s %s", async and "async" or "sync", opts.project_root, opts.path)
|
||||
|
||||
if async and callback then
|
||||
-- async, always call back
|
||||
self:_run_git_job(function()
|
||||
log.profile_end(profile)
|
||||
|
||||
self:_finalise(opts)
|
||||
|
||||
callback(self.output)
|
||||
end)
|
||||
else
|
||||
-- sync, maybe call back
|
||||
self:_run_git_job()
|
||||
self:_wait()
|
||||
|
||||
log.profile_end(profile)
|
||||
|
||||
self:_finalise(opts)
|
||||
|
||||
if callback then
|
||||
callback(self.output)
|
||||
else
|
||||
return self.output
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
function Runner.setup(opts)
|
||||
Runner.config = {}
|
||||
Runner.config.git_async = opts.experimental.git.async
|
||||
end
|
||||
|
||||
return Runner
|
||||
|
||||
Reference in New Issue
Block a user