aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJustin M. Keyes <justinkz@gmail.com>2024-01-27 10:40:30 -0800
committerGitHub <noreply@github.com>2024-01-27 10:40:30 -0800
commit2cd76a758b4511748d9482e5af58162a608516b4 (patch)
tree78b62d3994171c769eb17061d097ec821d5504e3
parent17b298b7c8a29ac3d54ea7adfa0e2ea09528e200 (diff)
downloadrneovim-2cd76a758b4511748d9482e5af58162a608516b4.tar.gz
rneovim-2cd76a758b4511748d9482e5af58162a608516b4.tar.bz2
rneovim-2cd76a758b4511748d9482e5af58162a608516b4.zip
docs(lua): update ":{range}lua" docs + error message #27231
- `:lua (no file)` is misleading because `:lua` never takes a file arg, unlike `:source`. - Update various related docs.
-rw-r--r--runtime/doc/lua.txt15
-rw-r--r--runtime/doc/repeat.txt8
-rw-r--r--src/nvim/lua/executor.c30
-rw-r--r--src/nvim/runtime.c2
-rw-r--r--test/functional/lua/commands_spec.lua26
5 files changed, 49 insertions, 32 deletions
diff --git a/runtime/doc/lua.txt b/runtime/doc/lua.txt
index fecdfd9bd0..7aa2fd5a6f 100644
--- a/runtime/doc/lua.txt
+++ b/runtime/doc/lua.txt
@@ -255,10 +255,13 @@ arguments separated by " " (space) instead of "\t" (tab).
:lua =jit.version
<
:{range}lua
- Executes the |[range]| in the current buffer as Lua code. Unlike |:source|,
- this will execute the specified lines regardless of the extension or
- |'filetype'| of the buffer.
+ Executes buffer lines in {range} as Lua code. Unlike |:source|, this
+ always treats the lines as Lua code.
+ Example: select the following code and type ":lua<Enter>" to execute it: >lua
+ print(string.format(
+ 'unix time: %s', os.time()))
+<
*:lua-heredoc*
:lua << [trim] [{endmarker}]
{script}
@@ -271,10 +274,8 @@ arguments separated by " " (space) instead of "\t" (tab).
function! CurrentLineInfo()
lua << EOF
local linenr = vim.api.nvim_win_get_cursor(0)[1]
- local curline = vim.api.nvim_buf_get_lines(
- 0, linenr - 1, linenr, false)[1]
- print(string.format("Current line [%d] has %d bytes",
- linenr, #curline))
+ local curline = vim.api.nvim_buf_get_lines(0, linenr - 1, linenr, false)[1]
+ print(string.format('Line [%d] has %d bytes', linenr, #curline))
EOF
endfunction
<
diff --git a/runtime/doc/repeat.txt b/runtime/doc/repeat.txt
index 726d7a9591..ae827fa06f 100644
--- a/runtime/doc/repeat.txt
+++ b/runtime/doc/repeat.txt
@@ -192,11 +192,11 @@ Using Vim scripts *using-scripts*
For writing a Vim script, see chapter 41 of the user manual |usr_41.txt|.
*:so* *:source* *load-vim-script*
-:[range]so[urce] [file] Runs |Ex| commands or Lua code (".lua" files) from
+:[range]so[urce] [file] Runs |Ex-commands| or Lua code (".lua" files) from
[file].
- If no [file], the current buffer is used, and it is
- treated as Lua code if its 'filetype' is "lua" or its
- file name ends with ".lua".
+ If no [file], the current buffer is used and treated
+ as Lua code if 'filetype' is "lua" or its filename
+ ends with ".lua".
Triggers the |SourcePre| autocommand.
*:source!*
:[range]so[urce]! {file}
diff --git a/src/nvim/lua/executor.c b/src/nvim/lua/executor.c
index 3139e924a1..62e82175c3 100644
--- a/src/nvim/lua/executor.c
+++ b/src/nvim/lua/executor.c
@@ -1641,19 +1641,20 @@ bool nlua_is_deferred_safe(void)
return in_fast_callback == 0;
}
-/// Run lua string
+/// Executes Lua code.
///
-/// Used for :lua.
+/// Implements `:lua` and `:lua ={expr}`.
///
-/// @param eap Vimscript command being run.
+/// @param eap Vimscript `:lua {code}`, `:{range}lua`, or `:lua ={expr}` command.
void ex_lua(exarg_T *const eap)
FUNC_ATTR_NONNULL_ALL
{
+ // ":{range}lua"
if (eap->addr_count > 0 || *eap->arg == NUL) {
if (eap->addr_count > 0 && *eap->arg == NUL) {
cmd_source_buffer(eap, true);
} else {
- semsg(_(e_invarg2), "exactly one of {chunk} and {range} required");
+ semsg(_(e_invarg2), "exactly one of {chunk} or {range} required");
}
return;
}
@@ -1664,13 +1665,14 @@ void ex_lua(exarg_T *const eap)
xfree(code);
return;
}
- // When =expr is used transform it to vim.print(expr)
+
+ // ":lua {code}", ":={expr}" or ":lua ={expr}"
+ //
+ // When "=expr" is used transform it to "vim.print(expr)".
if (eap->cmdidx == CMD_equal || code[0] == '=') {
size_t off = (eap->cmdidx == CMD_equal) ? 0 : 1;
len += sizeof("vim.print()") - 1 - off;
- // code_buf needs to be 1 char larger then len for null byte in the end.
- // lua nlua_typval_exec doesn't expect null terminated string so len
- // needs to end before null byte.
+ // `nlua_typval_exec` doesn't expect NUL-terminated string so `len` must end before NUL byte.
char *code_buf = xmallocz(len);
vim_snprintf(code_buf, len + 1, "vim.print(%s)", code + off);
xfree(code);
@@ -1682,11 +1684,11 @@ void ex_lua(exarg_T *const eap)
xfree(code);
}
-/// Run lua string for each line in range
+/// Executes Lua code for-each line in a buffer range.
///
-/// Used for :luado.
+/// Implements `:luado`.
///
-/// @param eap Vimscript command being run.
+/// @param eap Vimscript `:luado {code}` command.
void ex_luado(exarg_T *const eap)
FUNC_ATTR_NONNULL_ALL
{
@@ -1763,11 +1765,11 @@ void ex_luado(exarg_T *const eap)
redraw_curbuf_later(UPD_NOT_VALID);
}
-/// Run lua file
+/// Executes Lua code from a file location.
///
-/// Used for :luafile.
+/// Implements `:luafile`.
///
-/// @param eap Vimscript command being run.
+/// @param eap Vimscript `:luafile {file}` command.
void ex_luafile(exarg_T *const eap)
FUNC_ATTR_NONNULL_ALL
{
diff --git a/src/nvim/runtime.c b/src/nvim/runtime.c
index 77a22b6fd1..98e9d6c9e6 100644
--- a/src/nvim/runtime.c
+++ b/src/nvim/runtime.c
@@ -2014,7 +2014,7 @@ void cmd_source_buffer(const exarg_T *const eap, bool ex_lua)
};
if (ex_lua || strequal(curbuf->b_p_ft, "lua")
|| (curbuf->b_fname && path_with_extension(curbuf->b_fname, "lua"))) {
- char *name = ex_lua ? ":lua (no file)" : ":source (no file)";
+ char *name = ex_lua ? ":{range}lua" : ":source (no file)";
nlua_source_using_linegetter(get_str_line, (void *)&cookie, name);
} else {
source_using_linegetter((void *)&cookie, get_str_line, ":source (no file)");
diff --git a/test/functional/lua/commands_spec.lua b/test/functional/lua/commands_spec.lua
index 083f6f3541..b759d0e2c4 100644
--- a/test/functional/lua/commands_spec.lua
+++ b/test/functional/lua/commands_spec.lua
@@ -22,7 +22,7 @@ local remove_trace = helpers.remove_trace
before_each(clear)
-describe(':lua command', function()
+describe(':lua', function()
it('works', function()
eq('', exec_capture('lua vim.api.nvim_buf_set_lines(1, 1, 2, false, {"TEST"})'))
eq({ '', 'TEST' }, api.nvim_buf_get_lines(0, 0, 100, false))
@@ -54,10 +54,11 @@ describe(':lua command', function()
)
)
end)
+
it('throws catchable errors', function()
for _, cmd in ipairs({ 'lua', '1lua chunk' }) do
eq(
- 'Vim(lua):E475: Invalid argument: exactly one of {chunk} and {range} required',
+ 'Vim(lua):E475: Invalid argument: exactly one of {chunk} or {range} required',
pcall_err(command, cmd)
)
end
@@ -75,9 +76,11 @@ describe(':lua command', function()
)
eq({ '' }, api.nvim_buf_get_lines(0, 0, 100, false))
end)
+
it('works with NULL errors', function()
eq([=[Vim(lua):E5108: Error executing lua [NULL]]=], exc_exec('lua error(nil)'))
end)
+
it('accepts embedded NLs without heredoc', function()
-- Such code is usually used for `:execute 'lua' {generated_string}`:
-- heredocs do not work in this case.
@@ -89,12 +92,14 @@ describe(':lua command', function()
]])
eq({ '', 'ETTS', 'TTSE', 'STTE' }, api.nvim_buf_get_lines(0, 0, 100, false))
end)
+
it('preserves global and not preserves local variables', function()
eq('', exec_capture('lua gvar = 42'))
eq('', exec_capture('lua local lvar = 100500'))
eq(NIL, fn.luaeval('lvar'))
eq(42, fn.luaeval('gvar'))
end)
+
it('works with long strings', function()
local s = ('x'):rep(100500)
@@ -199,17 +204,26 @@ describe(':lua command', function()
)
end)
- it('works with range in current buffer', function()
+ it('with range', function()
local screen = Screen.new(40, 10)
screen:attach()
- api.nvim_buf_set_lines(0, 0, 0, 0, { 'function x() print "hello" end', 'x()' })
- feed(':1,2lua<CR>')
+ api.nvim_buf_set_lines(0, 0, 0, 0, { 'nonsense', 'function x() print "hello" end', 'x()' })
+
+ -- ":{range}lua" fails on invalid Lua code.
+ eq(
+ [[:{range}lua: Vim(lua):E5107: Error loading lua [string ":{range}lua"]:0: '=' expected near '<eof>']],
+ pcall_err(command, '1lua')
+ )
+
+ -- ":{range}lua" executes valid Lua code.
+ feed(':2,3lua<CR>')
screen:expect {
grid = [[
+ nonsense |
function x() print "hello" end |
x() |
^ |
- {1:~ }|*6
+ {1:~ }|*5
hello |
]],
attr_ids = {