What is the most efficient way to call a Neovim function using Lua. I am able to call the sign_define Vim script function using the nvim_command procedure. I struggle with calling it with the nvim_call_function due to (assuming) converting the lua table to a Vim script dict.

-- Change default signcolumn signs for LSP

api.nvim_call_function('sign_define', {"LspDiagnosticsErrorSign", '{"text" : "", "texthl" : "LspDiagnosticsError"}'})

api.nvim_command('call sign_define("LspDiagnosticsWarningSign", {"text" : "", "texthl" : "LspDiagnosticsWarning"})')

Separately, I wonder if there may be errors due to lua's lack of Unicode support (stdlib).

2 Answers 2


It must be

vim.api.nvim_call_function("sign_define", {"LspDiagnosticsErrorSign",
    {text = "whatever", texthl = "LspDiagnosticsError"}})

as Lua has its own syntax for defining tables. Or, at least in 0.5, you can do

    {text = "whatever", texthl = "LspDiagnosticsError"})

which looks a bit nicer.

Separately, I wonder if there may be errors due to lua's lack of Unicode support (stdlib).

Well, that depends on how the engine was built, but, yes, you may easily catch such sort of errors. For example, io.open() may succeed, but the name of a created file will look "funny", and so on. But at least Lua should not segfault.

  • 1
    kudos for using vim.fn
    – tkolleh
    Commented Aug 24, 2020 at 3:10
  • For any having troubles, LspDiagnosticsErrorSign to LspDiagnosticsSignError .. Commented Dec 14, 2020 at 8:56

In addition to Matt's great answer, you can use vim.fn for your own or plugin vimscript functions.

To call autoload functions you'll need to change the syntax because # isn't a valid part of a Lua identifier. vim.fn is a table and in Lua, vim.fn.func and vim.fn['func'] are equivalent. So when the names have # you can pass them with this table index syntax:

:lua print(vim.fn['fugitive#GitVersion']())
:lua print(vim.api.nvim_call_function('fugitive#GitVersion', {}))
:echo fugitive#GitVersion()

Of course vim.api.nvim_call_function works as normal for these kinds of functions since the function name is passed as a string.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.