Skip to content

Commit

Permalink
fix(filetype): match on <afile> rather than <abuf> (#16943)
Browse files Browse the repository at this point in the history
Filetype detection runs on BufRead and BufNewFile autocommands, both of
which can fire without an underlying buffer, so it's incorrect to use
<abuf> to determine the file path. Instead, match on <afile> and assume
that the buffer we're operating on is the current buffer. This is the
same assumption that filetype.vim makes, so it should be safe.
  • Loading branch information
gpanders committed Jan 5, 2022
1 parent 55a59e5 commit f40ce34
Show file tree
Hide file tree
Showing 3 changed files with 16 additions and 17 deletions.
2 changes: 1 addition & 1 deletion runtime/filetype.lua
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ end

vim.cmd [[
augroup filetypedetect
au BufRead,BufNewFile * call v:lua.vim.filetype.match(str2nr(expand('<abuf>')))
au BufRead,BufNewFile * call v:lua.vim.filetype.match(expand('<afile>'))
" These *must* be sourced after the autocommand above is created
runtime! ftdetect/*.vim
Expand Down
13 changes: 9 additions & 4 deletions runtime/lua/vim/filetype.lua
Original file line number Diff line number Diff line change
Expand Up @@ -1449,15 +1449,20 @@ local function dispatch(ft, path, bufnr, ...)
end

---@private
function M.match(bufnr)
local path = api.nvim_buf_get_name(bufnr)
function M.match(name, bufnr)
-- When fired from the main filetypedetect autocommand the {bufnr} argument is omitted, so we use
-- the current buffer. The {bufnr} argument is provided to allow extensibility in case callers
-- wish to perform filetype detection on buffers other than the current one.
bufnr = bufnr or api.nvim_get_current_buf()

-- First check for the simple case where the full path exists as a key
local path = vim.fn.fnamemodify(name, ":p")
if dispatch(filename[path], path, bufnr) then
return
end

-- Next check against just the file name
local tail = vim.fn.fnamemodify(path, ":t")
local tail = vim.fn.fnamemodify(name, ":t")
if dispatch(filename[tail], path, bufnr) then
return
end
Expand All @@ -1477,7 +1482,7 @@ function M.match(bufnr)
end

-- Finally, check file extension
local ext = vim.fn.fnamemodify(path, ":e")
local ext = vim.fn.fnamemodify(name, ":e")
if dispatch(extension[ext], path, bufnr) then
return
end
Expand Down
18 changes: 6 additions & 12 deletions test/functional/lua/filetype_spec.lua
Original file line number Diff line number Diff line change
Expand Up @@ -24,8 +24,7 @@ describe('vim.filetype', function()
rs = 'radicalscript',
},
})
vim.api.nvim_buf_set_name(0, 'main.rs')
vim.filetype.match(0)
vim.filetype.match('main.rs')
return vim.bo.filetype
]])
end)
Expand All @@ -40,8 +39,7 @@ describe('vim.filetype', function()
['main.rs'] = 'somethingelse',
},
})
vim.api.nvim_buf_set_name(0, 'main.rs')
vim.filetype.match(0)
vim.filetype.match('main.rs')
return vim.bo.filetype
]])
end)
Expand All @@ -53,8 +51,7 @@ describe('vim.filetype', function()
['s_O_m_e_F_i_l_e'] = 'nim',
},
})
vim.api.nvim_buf_set_name(0, 's_O_m_e_F_i_l_e')
vim.filetype.match(0)
vim.filetype.match('s_O_m_e_F_i_l_e')
return vim.bo.filetype
]])

Expand All @@ -66,8 +63,7 @@ describe('vim.filetype', function()
[root .. '/.config/fun/config'] = 'dosini',
},
})
vim.api.nvim_buf_set_name(0, root .. '/.config/fun/config')
vim.filetype.match(0)
vim.filetype.match(root .. '/.config/fun/config')
return vim.bo.filetype
]], root))
end)
Expand All @@ -80,8 +76,7 @@ describe('vim.filetype', function()
[root .. '/blog/.*%.txt'] = 'markdown',
}
})
vim.api.nvim_buf_set_name(0, root .. '/blog/why_neovim_is_awesome.txt')
vim.filetype.match(0)
vim.filetype.match(root .. '/blog/why_neovim_is_awesome.txt')
return vim.bo.filetype
]], root))
end)
Expand All @@ -97,8 +92,7 @@ describe('vim.filetype', function()
end,
}
})
vim.api.nvim_buf_set_name(0, 'relevant_to_me')
vim.filetype.match(0)
vim.filetype.match('relevant_to_me')
return vim.bo.filetype
]])
end)
Expand Down

0 comments on commit f40ce34

Please sign in to comment.