Taking Neovim to the Moon - part II
Tags: neovim, vim, programming, webdev
Published: 2023-01-10 14:13:03


Hello again! In this article, I continue with the Neovim configuration using Lua. If you missed it, click [here](https://blog.elvessousa.com.br/en/post/neovim-lua-config) to see the previous article. Without reading it, it will not be possible to understand the text that follows.

## Minor substitutions

Shortly after publishing the previous article, I was informed (thanks, [Sérgio Araújo](https://dev.to/voyeg3r)!) that the extension used to ease language server's setup, **Neovim LSP Installer**, has been retired. Its successor is **Mason**, which basically has the same tools. Command names change, but the transition is smooth: on the surface, just the name and a better UI presentation. What really changes is the internal part, where, according to the developer, it's easier to create new features and test.

To make the switch, just change the lines where the LSP Installer is quoted:

```lua
packer.startup(function()
  -- use("williamboman/nvim-lsp-installer")
  use("williamboman/mason.nvim")
end)

-- LSP Installer
require("mason").setup()
```

After that, run the `:PackerSync` command and restart Neovim to apply the changes.

## Modules

### Splitting the config file into modules

I purposely did all the configuration in just one Lua file in the previous article. This was done to make it easier to understand how different parts work together. You can keep it that way if you like, but if you need to use a lot of extensions, working on a single file will become cumbersome.

The file structure I use is as follows:

```
lua
├── configs
│  ├── completion.lua
│  ├── diagnostics.lua
│  ├── formatting.lua
│  ├── highlighting.lua
│  ├── keymaps.lua
│  ├── languages.lua
│  ├── options.lua
│  ├── plugins.lua
│  └── theming.lua
└── init.lua
```

Basically, it's a folder called `configs/`, with several `*.lua` files inside. They were named according to their respective roles. All theme settings are in `theming.lua` and editor options in `options.lua`, for example. My categorization was pretty simple. Feel free to make your own.

To split the single file into modules, it's no big deal. In my case, I just used the comments that I had placed as separators in the file as guides. Each comment like that, a new file.

To make it clearer, here's an example:

```lua
---------------------------------
-- Options
---------------------------------
local set = vim.opt

set.background = "dark"
set.clipboard = "unnamedplus"

---------------------------------
-- Plugins
---------------------------------
local packer = require("packer")
vim.cmd([[packadd packer.nvim]])

packer.startup(function()
	use("hrsh7th/cmp-buffer")
	use("hrsh7th/cmp-cmdline")
  ...
end)
```

Using the structure above, what follows after the `-- Options` comment will be placed in the `configs/options.lua` file; what follows after the `-- Plugins` comment in the `configs/plugins.lua` file, and so on.

### Index file

The Lua language uses `init.lua` files as an index, similar to `index.html` in HTML or `main.rs` in Rust. Our `init.lua`, which previously contained all the configuration, will now only refer to the files. To import them in the file, just use the `require()` function passing the argument in the format `<directory>.<filename>`:

```lua
require("configs.options")
require("configs.plugins")
require("configs.highlighting")
require("configs.theming")
require("configs.completion")
require("configs.diagnostics")
require("configs.languages")
require("configs.formatting")
require("configs.keymaps")
```

### Where to place these files

For these files to take effect, simply place them in the `~/.config/nvim` folder. If there are no errors, everything will work fine when restarting Neovim. But if you're like me, and prefer to leave everything versioned in a GIT repository, I recommend creating symlinks to the `init.lua` file and the `lua` directory inside the `~/.config/nvim` folder. To create them, just issue these commands in the terminal:

```shell
$ cd ~/.config/nvim/
$ ln -sf ~/.dotfiles/editors/nvim/init.lua .
$ ln -sf ~/.dotfiles/editors/nvim/lua .
```

If you list the directory contents using the `ls -l` command, you will see something like this:

```shell
lrwxrwxrwx 48 user 22 out 18:50 init.lua -> /home/user/.dotfiles/editors/nvim/init.lua
lrwxrwxrwx 43 user 20 out 20:21 lua -> /home/user/.dotfiles/editors/nvim/lua
```

Note that `.dotfiles/editors/nvim` is just where I keep my files, so this may be different in your case. With this, you don't need to repeat all the setup from scratch again, and you can use the same files on other machines.

---

I believe that with these adjustments, you will have a good structure to configure your Neovim and extend it to suit your needs.

If you want to see the complete code, with all the changes I made, I've left the link to my `.dotfiles` repository below. This repo also includes the old `init.lua` made in the [previous article](https://blog.elvessousa.com.br/en/post/neovim-lua-config), just in case. It has been renamed to `init.lua.old`.

See you later!

### Links

- [This article in Portuguese](https://blog.elvessousa.com.br/post/neovim-lua-2)
- [My dotfiles](https://github.com/elvessousa/.dotfiles)
- [Mason](https://github.com/williamboman/mason.nvim)

---

If this article helped you in some way, consider [donating](https://www.buymeacoffee.com/elvessousa). This will help me to create more content like this!