feat(mini.files): make file system actions LSP aware#2340
feat(mini.files): make file system actions LSP aware#2340TheLeoP wants to merge 15 commits intonvim-mini:mainfrom
Conversation
|
To test the PR using with the following content -- main.lua
local something = require("something").something
something()
-- something.lua
local M = {}
M.something = function()
print("something")
end
return Myou can then |
|
The tests errors seem to go away if I comment out Line 2898 in 134f9dd and Line 2911 in 134f9dd But I'm not sure why. In particular, the problematic lines seem to be Line 2754 in 134f9dd and Line 2802 in 134f9dd changing them to local clients = {}seems to also make the test pass. Are these tests specially time sensitive? I can't think of another reason of why they would be failing |
echasnovski
left a comment
There was a problem hiding this comment.
Thanks for the PR!
There are at least two good things: the LSP complexity seems to be understood and managed (the worst part for me :) ) and there is a room for making it more concise.
I don't think so. Probably, some logic has been broken. Didn't read too much into the code.
Restricting this functionality to only Neovim<0.11 is fine.
I am okay with these checks for I'll also take a look into how to better handle the "close on lost focus" in 'mini.files'. It will probably have to be "don't close if inside non-normal buffer in a floating window" type of exception. |
Okay, I've looked into this. Going the "don't close explorer if in floating window" goes against some of the use cases that originally prompted the tracking of lost focus. Like "I want to I think the best compromise here would be to temporarily adjust Something like this (as of the current state of this PR) seems to work: diff --git a/lua/mini/files.lua b/lua/mini/files.lua
index 304e895f..fce1bbb7 100644
--- a/lua/mini/files.lua
+++ b/lua/mini/files.lua
@@ -1540,7 +1540,7 @@ end
H.explorer_track_lost_focus = function()
local track = vim.schedule_wrap(function()
local ft = vim.bo.filetype
- if ft == 'minifiles' or ft == 'minifiles-help' then return end
+ if H.skip_track_lost_focus or ft == 'minifiles' or ft == 'minifiles-help' then return end
local cur_win_id = vim.api.nvim_get_current_win()
MiniFiles.close()
pcall(vim.api.nvim_set_current_win, cur_win_id)
@@ -2753,6 +2753,15 @@ H.lsp_will_fs_do = function(action, params)
local full_method = 'workspace/' .. method .. 'Files'
local clients = vim.lsp.get_clients({ method = full_method })
+ local ui_select_orig = vim.ui.select
+ vim.ui.select = function(items, opts, on_choice)
+ H.skip_track_lost_focus = MiniFiles.get_explorer_state() ~= nil
+ ui_select_orig(items, opts, function(...)
+ H.skip_track_lost_focus, vim.ui.select = nil, ui_select_orig
+ on_choice(...)
+ end)
+ end
+
-- TODO(TheLeoP): configurable timeout
local timeout = 1000
for _, client in ipairs(clients) doOne thing to extra consider is whether there will be any side effects if Thinking about it more, maybe it is a good idea to have this kind of mock in general for the whole duration of the explorer. Will also work nicely with something like 'mini.snippets' (which can use |
Yeah, ignoring tracking lost focus while I tried it with this PR and:
|
|
Thanks for your feedback! I'll be a bit busy today and tomorrow, so I'll address your comments and I'll keep working on this PR on Sunday |
Soo... I spent some time investigating in the hopes of opening an issue in neovim/neovim to drop the
Repro steps for what I did:
|
d6f5b42 to
18ca59f
Compare
|
The bulk LSP request/notifications should be working now. I left them on separated commits to make reviewing a bit easier. Let me know if you have any more feedback regarding the implementation. After that is done, I'll focus on creating some tests. What would be your preference for testing this? My guess is that it would be to mock a language server. I can take a look at |
echasnovski
left a comment
There was a problem hiding this comment.
This is visibly better now, thanks! Added the next round of review.
This should now work on the latest |
Refactor `H.lsp_{will,did}_fs_do_metho` into a single function
Execute LSP requests/notifications in bulk inside `H.fs_actions_apply`
`string.lower()` -> `vim.fn.tolower()`
Add LSP filter for directory/file
Fix: join all checks within a single filter with AND and all the filters for a given server with OR
This seems to be need to make all tests pass. Can `from` be nil outside of tests?
refactor: more concise variable declaration
refactor: simplify lsp params computation logic
refactor: perform checks for willXxx
|
I just tested the latest changes on |
refactor: Simplify `lsp_fs_hook` code
Details: - Perform filter when converting diffs into LSP file actions. - Construct a single filter function instead of several ones. - Do not use `fs_get_type()` inside a filter for `matches` since the file/directory may not exist on disk. Instead rely on the convention that if file path ends with '/' in the diff - it is a directory. - Do not use `vim.iter` in favor of explicit loops.
|
To spare both of us the back and forth about mine vague "make less nesting" suggestion, I've pushed what I think is a reasonable improvement (4b300bc). It did increase line count by 12 lines, but this is probably due to comments, new robustness checks, and performance improvements (mostly by avoiding doing things when they are not needed). This should work okay now. Please double check the new code. If you notice an incorrect behavior, please point that out. After that - squash all commits before it. Now the less fun part - tests. Yes, I'd like this to be done by an explicit new mocked LSP server (there are 'tests/mock-lsp' examples for reference). It essentially should test:
|
Addresses #2215
This is a proof of concept to test the idea of including this kind of LSP support inside of mini.files. It may not be merged at all or it may help to add new autocmds to allow users/other plugins to implement this themselves.
A few things to take into account
H.fs_do.deletehad to be changed to allow checkingsuccessa single time before triggeringdidDeleteFilenotifications (actually, it seems like I broke something)timeoutforclient:request_syncis harcodedvim.glob.to_lpeghas a bug prior to 0.11 that requires manually sorting items inside brackets as a workaround,client:request_sync/client:notifyare not methods prior to 0.11, etc)libuvdoes not offer an abstraction on top of it. Maybefs_statrelated function would work on Windows with the same semantics, I haven't tested it yet)