fix(conflict): keep TextChanged autocmd alive after resolution

Problem: resolving the last conflict called M.detach(), which cleared
attached_buffers[bufnr]. The TextChanged callback then returned true,
permanently deleting the autocmd. Undo restored conflict markers but
nothing re-highlighted or re-suppressed diagnostics.

Solution: inline the cleanup in refresh() instead of calling detach().
Keep attached_buffers set so the autocmd survives. Re-suppress
diagnostics when conflicts reappear after undo.
This commit is contained in:
Barrett Ruth 2026-02-07 19:42:29 -05:00
parent bae86c5fd9
commit 35cb13419c
2 changed files with 42 additions and 1 deletions

View file

@ -214,11 +214,19 @@ end
local function refresh(bufnr, config)
local regions = parse_buffer(bufnr)
if #regions == 0 then
M.detach(bufnr)
vim.api.nvim_buf_clear_namespace(bufnr, ns, 0, -1)
if diagnostics_suppressed[bufnr] then
pcall(vim.diagnostic.enable, true, { bufnr = bufnr })
diagnostics_suppressed[bufnr] = nil
end
vim.api.nvim_exec_autocmds('User', { pattern = 'DiffsConflictResolved' })
return
end
apply_highlights(bufnr, regions, config)
if config.disable_diagnostics and not diagnostics_suppressed[bufnr] then
pcall(vim.diagnostic.enable, false, { bufnr = bufnr })
diagnostics_suppressed[bufnr] = true
end
end
---@param bufnr integer

View file

@ -631,6 +631,39 @@ describe('conflict', function()
helpers.delete_buffer(bufnr)
end)
it('re-highlights when markers return after resolution', function()
local bufnr = create_file_buffer({
'<<<<<<< HEAD',
'local x = 1',
'=======',
'local x = 2',
'>>>>>>> feature',
})
vim.api.nvim_set_current_buf(bufnr)
local cfg = default_config()
conflict.attach(bufnr, cfg)
assert.is_true(#get_extmarks(bufnr) > 0)
vim.api.nvim_win_set_cursor(0, { 2, 0 })
conflict.resolve_ours(bufnr, cfg)
assert.are.equal(0, #get_extmarks(bufnr))
vim.api.nvim_buf_set_lines(bufnr, 0, -1, false, {
'<<<<<<< HEAD',
'local x = 1',
'=======',
'local x = 2',
'>>>>>>> feature',
})
vim.api.nvim_exec_autocmds('TextChanged', { buffer = bufnr })
assert.is_true(#get_extmarks(bufnr) > 0)
conflict.detach(bufnr)
helpers.delete_buffer(bufnr)
end)
it('detaches after last conflict resolved', function()
local bufnr = create_file_buffer({
'<<<<<<< HEAD',