summaryrefslogtreecommitdiffstatshomepage
diff options
context:
space:
mode:
authorBarrett Ruth <62671086+barrettruth@users.noreply.github.com>2026-04-23 15:01:37 -0400
committergithub-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>2026-04-23 23:38:56 +0000
commit654c964d1aacaf76e884f975e45792d6fc364b12 (patch)
tree219c51b297377cf899e3218c0409a5d754b99c86
parent0bd6e62509b82c57c825e80842feb1c6ccb4ff15 (diff)
fix(trust): hash unchanged empty buffers as empty files #39027
Problem: `vim.secure.trust()` hashes an unchanged empty buffer as a newline, so trusting an empty file by buffer never works. Solution: Hash unchanged empty-buffers `''` so buffer-based trust matches the on-disk empty file. (cherry picked from commit 0a8218a2b40fa8f6b533605db4377ff89250711c)
-rw-r--r--runtime/lua/vim/secure.lua17
-rw-r--r--test/functional/ex_cmds/trust_spec.lua13
-rw-r--r--test/functional/lua/secure_spec.lua14
3 files changed, 39 insertions, 5 deletions
diff --git a/runtime/lua/vim/secure.lua b/runtime/lua/vim/secure.lua
index 9f5463ac98..4a89139679 100644
--- a/runtime/lua/vim/secure.lua
+++ b/runtime/lua/vim/secure.lua
@@ -39,11 +39,18 @@ local function compute_hash(fullpath, bufnr)
end
if bufnr then
- local newline = vim.bo[bufnr].fileformat == 'unix' and '\n' or '\r\n'
- contents =
- table.concat(vim.api.nvim_buf_get_lines(bufnr --[[@as integer]], 0, -1, false), newline)
- if vim.bo[bufnr].endofline then
- contents = contents .. newline
+ local is_unchanged_empty = vim.api.nvim_buf_call(bufnr, function()
+ return not vim.bo[bufnr].modified and vim.fn.line2byte(1) == -1
+ end)
+ if is_unchanged_empty then
+ contents = ''
+ else
+ local newline = vim.bo[bufnr].fileformat == 'unix' and '\n' or '\r\n'
+ contents =
+ table.concat(vim.api.nvim_buf_get_lines(bufnr --[[@as integer]], 0, -1, false), newline)
+ if vim.bo[bufnr].endofline then
+ contents = contents .. newline
+ end
end
else
do
diff --git a/test/functional/ex_cmds/trust_spec.lua b/test/functional/ex_cmds/trust_spec.lua
index 8cfb276706..ee823a6ce7 100644
--- a/test/functional/ex_cmds/trust_spec.lua
+++ b/test/functional/ex_cmds/trust_spec.lua
@@ -12,15 +12,18 @@ local fn = n.fn
describe(':trust', function()
local xstate = 'Xstate_ex_trust'
local test_file = 'Xtest_functional_ex_cmds_trust'
+ local empty_file = 'Xtest_functional_ex_cmds_trust_empty'
before_each(function()
n.mkdir_p(vim.fs.joinpath(xstate, is_os('win') and 'nvim-data' or 'nvim'))
t.write_file(test_file, 'test')
+ t.write_file(empty_file, '')
clear { env = { XDG_STATE_HOME = xstate } }
end)
after_each(function()
os.remove(test_file)
+ os.remove(empty_file)
n.rmdir(xstate)
end)
@@ -62,6 +65,16 @@ describe(':trust', function()
assert_trust_entry('')
end)
+ it('trust an empty file using current buffer', function()
+ local cwd = fn.getcwd()
+ local hash = fn.sha256(assert(t.read_file(empty_file)))
+
+ command('edit ' .. empty_file)
+ matches('^Allowed in trust database%: ".*' .. empty_file .. '"$', exec_capture('trust'))
+ local trust = t.read_file(fn.stdpath('state') .. pathsep .. 'trust')
+ eq(string.format('%s %s', hash, cwd .. pathsep .. empty_file), vim.trim(trust))
+ end)
+
it('deny then trust then remove a file using current buffer', function()
local cwd = fn.getcwd()
local hash = fn.sha256(assert(t.read_file(test_file)))
diff --git a/test/functional/lua/secure_spec.lua b/test/functional/lua/secure_spec.lua
index c68637f00a..52a4ac9710 100644
--- a/test/functional/lua/secure_spec.lua
+++ b/test/functional/lua/secure_spec.lua
@@ -280,6 +280,7 @@ describe('vim.secure', function()
describe('trust()', function()
local xstate = 'Xstate_lua_secure'
local test_file = 'Xtest_functional_lua_secure'
+ local empty_file = 'Xtest_functional_lua_secure_empty'
local test_dir = 'Xtest_functional_lua_secure_dir'
setup(function()
@@ -289,11 +290,13 @@ describe('vim.secure', function()
before_each(function()
n.mkdir_p(vim.fs.joinpath(xstate, is_os('win') and 'nvim-data' or 'nvim'))
t.write_file(test_file, 'test')
+ t.write_file(empty_file, '')
t.mkdir(test_dir)
end)
after_each(function()
os.remove(test_file)
+ os.remove(empty_file)
n.rmdir(test_dir)
n.rmdir(xstate)
end)
@@ -328,6 +331,17 @@ describe('vim.secure', function()
assert_trust_entry('')
end)
+ it('trust an empty file using bufnr', function()
+ local cwd = fn.getcwd()
+ local hash = fn.sha256(assert(read_file(empty_file)))
+ local full_path = cwd .. pathsep .. empty_file
+
+ command('edit ' .. empty_file)
+ eq({ true, full_path }, exec_lua([[return {vim.secure.trust({action='allow', bufnr=0})}]]))
+ local trust = assert(read_file(stdpath('state') .. pathsep .. 'trust'))
+ eq(string.format('%s %s', hash, full_path), vim.trim(trust))
+ end)
+
it('deny then trust then remove a file using bufnr', function()
local cwd = fn.getcwd()
local hash = fn.sha256(assert(read_file(test_file)))