MagicDuck / grug-far.nvim

Find And Replace plugin for neovim
MIT License
849 stars 25 forks source link

Grug-far crashes Neovim when using astgrep #234

Closed dpetka2001 closed 2 months ago

dpetka2001 commented 2 months ago

This happens only on latest Neovim nightly (not sure if it happened after a specific version, since I just started exploring Grugfar astgrep yesterday). On Neovim stable 0.10.1 it hasn't happened to me yet, so I guess it's ok.

It has to do something with statuscolumn I believe. I normally use LazyVim, which has a custom statuscolumn and the problem did not occur when statuscolumn = "" (just an empty string). I tried to repro this with just a very simple init.lua file outside of LazyVim and was able to repro.

This is the minimal repro where it crashes Neovim

-- DO NOT change the paths and don't remove the colorscheme
local root = vim.fn.fnamemodify("./.repro", ":p")

-- set stdpaths to use .repro
for _, name in ipairs({ "config", "data", "state", "cache" }) do
    vim.env[("XDG_%s_HOME"):format(name:upper())] = root .. "/" .. name
end

-- bootstrap lazy
local lazypath = root .. "/plugins/lazy.nvim"
-- local lazypath = vim.fn.expand("~/projects/plugins/lazy.nvim/")
if not vim.loop.fs_stat(lazypath) then
    vim.fn.system({ "git", "clone", "--filter=blob:none", "https://github.com/folke/lazy.nvim.git", lazypath })
end
vim.opt.runtimepath:prepend(lazypath)

vim.opt.statuscolumn = "1"

vim.g.mapleader = " "
vim.g.maplocalleader = ","

-- install plugins
local plugins = {
    { "folke/tokyonight.nvim" },

    {
        "MagicDuck/grug-far.nvim",
        opts = { headerMaxWidth = 80 },
        cmd = "GrugFar",
        keys = {
            {
                "<leader>sr",
                function()
                    local grug = require("grug-far")
                    local ext = vim.bo.buftype == "" and vim.fn.expand("%:e")
                    grug.open({
                        transient = true,
                        prefills = {
                            filesFilter = ext and ext ~= "" and "*." .. ext or nil,
                        },
                    })
                end,
                mode = { "n", "v" },
                desc = "Search and Replace",
            },
        },
    },
    -- add any other plugins here
}
require("lazy").setup(plugins, {
    root = root .. "/plugins",
})

vim.cmd.colorscheme("tokyonight")
-- add anything else here

Here follows a screencast of what's happening

Screencast_2024-08-30-11-09-50.webm

The error that it throws is

nvim: /home/runner/work/neovim/neovim/src/nvim/decoration.c:849: buf_signcols_count_range: Assertion `buf->b_signcols.count[prevwidth - 1] >= 0' failed

Not sure who is to blame here, the plugin or even Neovim. But in Neovim stable this does not happen and in Neovim latest nightly it does. In the above minimal repro you can see there is a line vim.opt.statuscolumn = "1". If you comment out that line, then the problem does not occur. But with statuscolumn set to whatever string, then Neovim crashes.

MagicDuck commented 2 months ago

My best guess is that it crashes cause grugfar uses the sign and fold column, but with that statuscolumn format neither is present… I wonder if it would be fixed if you include those in your statuscolumn setting:

%s sign column for currently drawn line %C fold column for currently drawn line

I only use the standard extmark api to add signs and it should not be the responsability of every consumer of that api to ensure that statuscolumn has a space for a sign, so I think the problem is with neovim nightly.

in the docs i see that statuscolumn option is marked as experimental, so maybe a symptom of that. I would report this as a bug in neovim or Lazyvim at the least since they have connections in neovim core and might be able to address it.

MagicDuck commented 2 months ago

Meanwhile you might be able to get around it by disabling icons that go in the sign column: Basically the 4 lines here https://github.com/MagicDuck/grug-far.nvim/blob/e0ba9711f82289f27df290a4a72682e047ce4fdb/lua/grug-far/opts.lua#L198

dpetka2001 commented 2 months ago

Thank you very much for your response. Were you able to reproduce with the minimal repro that I included? Because the minimal repro is independent of LazyVim. It just includes lazy.nvim and grug-far.

I tried with your first suggestion by changing vim.opt.statuscolumn = "%s %C" (there's a space between the 2 components but I also tried without any space between them) but unfortunately the same thing happened.

When I went with your second suggestion to disable the icons, then no problem occurs on nightly.

Like I said on stable I haven't run into this, only on nightly. What do you think should be done about this? I read on Neovim issue template, that when a crash is involved a stacktrace should also be included. I'm not familiar with this procedure. Would you be willing to open an issue at Neovim github repo if you deem it necessary?

Even vim.opt.statuscolumn = " " (a single space) triggers it.

dpetka2001 commented 2 months ago

Ok I believe I was able to get a backtrace after reading Neovim docs. I just hope I managed to do it the right way, since it's the first time doing this. I will open an issue at Neovim github repo. I will leave this open until I get a response there.

MagicDuck commented 2 months ago

weird, I can reproduce it with your reproduction steps

 ./nvim-macos-arm64/bin/nvim -u ~/repro.lua

but not if I run that same nightly version directly (so it runs my regular init)

 ./nvim-macos-arm64/bin/nvim
image
dpetka2001 commented 2 months ago

What do you have vim.opt.statuscolumn set to in your regular init? I was even able to reproduce it with the minimal.lua template from Neovim repo without using any plugin manager, just installing the plugin and appending the path to rtp and then require("grug-far").setup({}) as is mentioned in the issue I opened at Neovim repo.

MagicDuck commented 2 months ago

I don't set that in my vim.opt.statuscolumn config... 🤔

Btw, it appears to be this call that's crashing it: https://github.com/MagicDuck/grug-far.nvim/blob/e0ba9711f82289f27df290a4a72682e047ce4fdb/lua/grug-far/render/resultsList.lua#L36

dpetka2001 commented 2 months ago

If you don't set it to anything and it's just the default value (empty string) then it doesn't crash. For me it crashed because Lazyvim is also using a custom statuscolumn, but if i set that to just empty string then it doesn't crash. Unfortunately, i only know some basic programming in Lua and Python (so no programming experience whatsoever) and can't really understand what is going on in that call you mentioned. Sorry about that.

MagicDuck commented 2 months ago

no worries, I think I found the fix. If I swap the order of 2 lines in the clear() function it's all good! Seems like nightly version of nvim does not like to clear a namespace after lines on which the extmarks were, were removed.

Feel free to reopen if you still see the issue 😄

dpetka2001 commented 2 months ago

Does that mean i should close the issue at Neovim repo? It's not Neovim related?

MagicDuck commented 2 months ago

I just added a comment there, it's a regression I think... I would just leave it open and let them decide

dpetka2001 commented 2 months ago

Ok I see. Thank you very much for your quick response and help. I can confirm that after updating to latest grug-far version, the problem does not occur any more on Neovim nightly.

MagicDuck commented 2 months ago

Great! Thanks for confirming! 😄