A versão 0.5 do Neovim (nightly build) traz algumas mudanças como a integração do Lua como uma linguagem de primeira classe e o suporte a LSP embutido. Adeus CoC!
Você pode obter a versão 0.5 do Neovim aqui ou via homebrew:
$ brew unlink neovim
$ brew install neovim --HEAD
$ nvim --version
Migrando suas configurações para Lua
Vale dar uma passada pelo guia de primeiros passos usando Lua no Neovim e começar a migrar aos poucos suas configurações.
Exemplo do meu init.lua
:
vim.g.mapleader = ','
vim.api.nvim_set_keymap("n", ";", ":", { noremap = true })
vim.cmd [[
source ~/.config/nvim/config.vim
source ~/.config/nvim/plugins.vim
source ~/.config/nvim/settings.vim
source ~/.config/nvim/keymappings.vim
]]
require'config.lsp'
-- ... configs
Escolhi mudar o init.vim
para init.lua
e aos poucos ir migrando cada .vim
. Também mantenho por enquanto o mesmo gerenciador de plugins (vim-plug), então vamos instalar os novos plugins também por ele.
Configurando o LSP
A primeira coisa que precisamos fazer é instalar os plugins:
- neovim/nvim-lspconfig e kabouzeid/nvim-lspinstall para configurar e instalar os servers de cada linguagem;
- hrsh7th/nvim-compe para o auto completion
- glepnir/lspsaga.nvim para exibir melhor as mensagens e popups
Instalação, Inicialização e Comandos
Para que algum servidor comece a funcionar é necessário que ele seja instalado e inicializado no seu init.lua
. Com o nvim-lspinstall
podemos instalar com o comando :LspInstall <linguagem>
.
Utilizando no exemplo o tsserver
, vamos instalar com o comando :LspInstall typescript
(lista ref) e para iniciar os servidores que instalamos o seguinte trecho (em lua) é necessário:
require'lspsaga'.init_lsp_saga()
require'lspinstall'.setup()
local servers = require'lspinstall'.installed_servers()
for _, server in pairs(servers) do
require'lspconfig'[server].setup{}
end
Com isso você já terá o LSP rodando e pode testar abrindo um arquivo .ts
ou .tsx
e executar o comando :LspInfo
. O lspconfig
também vai aparecer no comando :checkhealth
então vale a pena executa-lo para verificar se está tudo ok.
Para configurar os atalhos você precisará passar uma função on_attach
no setup do lspconfig
, exemplo:
local on_attach = function(client, bufnr)
-- ...mappings
end
require'lspinstall'.setup()
local servers = require'lspinstall'.installed_servers()
for _, server in pairs(servers) do
require'lspconfig'[server].setup{ on_attach = on_attach }
end
Com os mappings:
local on_attach = function(_, bufnr)
local function buf_set_keymap(...) vim.api.nvim_buf_set_keymap(bufnr, ...) end
local function buf_set_option(...) vim.api.nvim_buf_set_option(bufnr, ...) end
local opts = { noremap = true, silent = true }
buf_set_option('omnifunc', 'v:lua.vim.lsp.omnifunc')
buf_set_keymap('n', '<leader>ca', ':Lspsaga code_action<CR>', opts)
buf_set_keymap('v', '<leader>ca', ':Lspsaga range_code_action<CR>', opts)
buf_set_keymap('n', '<leader>rn', ':Lspsaga rename<CR>', opts)
buf_set_keymap('n', 'K', ':Lspsaga hover_doc<CR>', opts)
buf_set_keymap('n', 'dn', ':Lspsaga diagnostic_jump_next<CR>', opts)
buf_set_keymap('n', 'dp', ':Lspsaga diagnostic_jump_prev<CR>', opts)
buf_set_keymap('n', 'gf', ':lua vim.lsp.buf.definition()<CR>', opts)
end
require'lspinstall'.setup()
local servers = require'lspinstall'.installed_servers()
for _, server in pairs(servers) do
require'lspconfig'[server].setup{ on_attach = on_attach }
end
Comandos:
-
<leader>ca
: Abre pop-up com as Code Actions -
<leader>rn
: Para renomear símbolo -
K
: Exibe a referência/documentação da seleção ou posição do cursor -
dn
edp
: Navega entre os diagnósticos -
gf
: Navegação de código
Mais comandos: aqui
Se você precisar configurar algo especifico para algum servidor, lembre-se de adicionar a chamada on_attach
para manter os comandos, exemplo (para linguagem lua):
require'lspconfig'.lua.setup {
on_attach = on_attach,
settings = {
Lua = {
diagnostics = {
globals = { 'vim' }
}
}
}
}
Para as sugestões e o auto completion, certifique-se de que você tenha os plugins SirVer/ultisnips e hrsh7th/vim-vsnip para sugestões de snippets. E então adicione o seguinte trecho:
require'compe'.setup {
enabled = true;
preselect = 'disable';
source = {
path = true;
buffer = true;
calc = true;
nvim_lsp = true;
nvim_lua = true;
vsnip = true;
ultisnips = true;
-- treesitter = true;
};
}
local t = function(str)
return vim.api.nvim_replace_termcodes(str, true, true, true)
end
local check_back_space = function()
local col = vim.fn.col('.') - 1
if col == 0 or vim.fn.getline('.'):sub(col, col):match('%s') then
return true
else
return false
end
end
vim.g.vsnip_filetypes = {
typescriptreact = {"typescript"}
}
_G.tab_complete_next = function()
if vim.fn.pumvisible() == 1 then
return t "<C-n>"
elseif vim.fn.call("vsnip#available", {1}) == 1 then
return t "<Plug>(vsnip-expand-or-jump)"
elseif check_back_space() then
return t "<Tab>"
else
return vim.fn['compe#complete']()
end
end
_G.tab_complete_prev = function()
if vim.fn.pumvisible() == 1 then
return t "<C-p>"
elseif vim.fn.call("vsnip#jumpable", {-1}) == 1 then
return t "<Plug>(vsnip-jump-prev)"
else
return t "<S-Tab>"
end
end
local opt = { expr = true, silent = true}
vim.api.nvim_set_keymap("i", "<Tab>", "v:lua.tab_complete_next()", opt)
vim.api.nvim_set_keymap("s", "<Tab>", "v:lua.tab_complete_next()", opt)
vim.api.nvim_set_keymap("i", "<S-Tab>", "v:lua.tab_complete_prev()", opt)
vim.api.nvim_set_keymap("s", "<S-Tab>", "v:lua.tab_complete_prev()", opt)
vim.api.nvim_set_keymap("i", "<CR>", 'compe#confirm("<CR>")', opt)
Com isso você tem o autocomplete funcionando e a navegação mapeada com Tab/Shift+Tab e o Esc para fechar o pop-up.
Obs: Caso você utilize o treesitter, remova o comentário das opções do setup.
É isso ☺️. Me diz ai o que achou e manda nos comentários como ficou seu nvim.
Abraços!
Top comments (3)
I can't use your config, I cloned your repo and install plugins but show error in console
lsp.lua:23: attempt to index field
'lua' (a nil value)
Press ENTER or type command to continue
Updated my config-nvim, more details: dev.to/enrsaid/neovim-initlua-buil...
Is there support to flutter like coc-flutter?