Skip to content

Commit 89c79cb

Browse files
committed
fix(#1831): improve fs_scandir error handling, add profiling
1 parent 87409bb commit 89c79cb

File tree

5 files changed

+62
-14
lines changed

5 files changed

+62
-14
lines changed

lua/nvim-tree/explorer/explore.lua

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ local function populate_children(handle, cwd, node, git_status)
1818
local nodes_by_path = utils.bool_record(node.nodes, "absolute_path")
1919
local filter_status = filters.prepare(git_status)
2020
while true do
21-
local name, t = vim.loop.fs_scandir_next(handle)
21+
local name, t = utils.fs_scandir_next_profiled(handle, cwd)
2222
if not name then
2323
break
2424
end
@@ -47,9 +47,9 @@ local function populate_children(handle, cwd, node, git_status)
4747
end
4848

4949
local function get_dir_handle(cwd)
50-
local handle = vim.loop.fs_scandir(cwd)
51-
if type(handle) == "string" then
52-
notify.error(handle)
50+
local handle, err = utils.fs_scandir_profiled(cwd)
51+
if err then
52+
notify.error(string.format("Failed exploring %s: %s", cwd, vim.inspect(err)))
5353
return
5454
end
5555
return handle

lua/nvim-tree/explorer/node-builders.lua

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -7,8 +7,8 @@ local M = {
77
}
88

99
function M.folder(parent, absolute_path, name)
10-
local handle = vim.loop.fs_scandir(absolute_path)
11-
local has_children = handle and vim.loop.fs_scandir_next(handle) ~= nil
10+
local handle = utils.fs_scandir_profiled(absolute_path)
11+
local has_children = handle and utils.fs_scandir_next_profiled(handle, absolute_path) ~= nil
1212

1313
local node = {
1414
type = "directory",
@@ -71,8 +71,8 @@ function M.link(parent, absolute_path, name)
7171
local is_dir_link = (link_to ~= nil) and vim.loop.fs_stat(link_to).type == "directory"
7272

7373
if is_dir_link then
74-
local handle = vim.loop.fs_scandir(link_to)
75-
has_children = handle and vim.loop.fs_scandir_next(handle) ~= nil
74+
local handle = utils.fs_scandir_profiled(link_to)
75+
has_children = handle and utils.fs_scandir_next_profiled(handle, link_to) ~= nil
7676
open = false
7777
nodes = {}
7878
end

lua/nvim-tree/explorer/reload.lua

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -36,9 +36,9 @@ end
3636

3737
function M.reload(node, git_status, unloaded_bufnr)
3838
local cwd = node.link_to or node.absolute_path
39-
local handle = vim.loop.fs_scandir(cwd)
40-
if type(handle) == "string" then
41-
notify.error(handle)
39+
local handle, err = utils.fs_scandir_profiled(cwd)
40+
if err then
41+
notify.error(string.format("Failed reloading %s: %s", cwd, vim.inspect(err)))
4242
return
4343
end
4444

@@ -56,8 +56,8 @@ function M.reload(node, git_status, unloaded_bufnr)
5656
local node_ignored = node.git_status == "!!"
5757
local nodes_by_path = utils.key_by(node.nodes, "absolute_path")
5858
while true do
59-
local ok, name, t = pcall(vim.loop.fs_scandir_next, handle)
60-
if not ok or not name then
59+
local name, t = utils.fs_scandir_next_profiled(handle, cwd)
60+
if not name then
6161
break
6262
end
6363

lua/nvim-tree/notify.lua

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ do
2424
if has_notify and notify_plugin then
2525
notify_plugin(msg, level, { title = "NvimTree" })
2626
else
27-
vim.notify("[NvimTree] " .. msg, level)
27+
vim.notify(string.format("[NvimTree] %s", vim.inspect(msg)), level)
2828
end
2929
end)
3030
end

lua/nvim-tree/utils.lua

Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
local Iterator = require "nvim-tree.iterators.node-iterator"
22
local notify = require "nvim-tree.notify"
3+
local log = require "nvim-tree.log"
34

45
local M = {
56
debouncers = {},
@@ -477,4 +478,51 @@ function M.is_nvim_tree_buf(bufnr)
477478
return false
478479
end
479480

481+
---Profile a call to vim.loop.fs_scandir
482+
---This should be removed following resolution of #1831
483+
---@param path string
484+
---@return userdata|nil uv_fs_t
485+
---@return string|nil type
486+
---@return string|nil err (fail)
487+
---@return string|nil name (fail)
488+
function M.fs_scandir_profiled(path)
489+
local pn = string.format("fs_scandir %s", path)
490+
local ps = log.profile_start(pn)
491+
492+
local handle, err, name = vim.loop.fs_scandir(path)
493+
494+
if err or name then
495+
log.line("profile", " %s err '%s'", pn, vim.inspect(err))
496+
log.line("profile", " %s name '%s'", pn, vim.inspect(name))
497+
end
498+
499+
log.profile_end(ps, pn)
500+
501+
return handle, err, name
502+
end
503+
504+
---Profile a call to vim.loop.fs_scandir_next
505+
---This should be removed following resolution of #1831
506+
---@param handle userdata uv_fs_t
507+
---@param tag string arbitrary
508+
---@return string|nil name
509+
---@return string|nil type
510+
---@return string|nil err (fail)
511+
---@return string|nil name (fail)
512+
function M.fs_scandir_next_profiled(handle, tag)
513+
local pn = string.format("fs_scandir_next %s", tag)
514+
local ps = log.profile_start(pn)
515+
516+
local n, t, err, name = vim.loop.fs_scandir_next(handle)
517+
518+
if err or name then
519+
log.line("profile", " %s err '%s'", pn, vim.inspect(err))
520+
log.line("profile", " %s name '%s'", pn, vim.inspect(name))
521+
end
522+
523+
log.profile_end(ps, pn)
524+
525+
return n, t, err, name
526+
end
527+
480528
return M

0 commit comments

Comments
 (0)