Skip to content

document how to setup RA for nvim automatically #2259

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 2 commits into from
Feb 24, 2025
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
33 changes: 29 additions & 4 deletions src/building/suggested.md
Original file line number Diff line number Diff line change
Expand Up @@ -120,10 +120,35 @@ create a `.vim/coc-settings.json`. The settings can be edited with
[`src/etc/rust_analyzer_settings.json`].

Another way is without a plugin, and creating your own logic in your
configuration. To do this you must translate the JSON to Lua yourself. The
translation is 1:1 and fairly straight-forward. It must be put in the
`["rust-analyzer"]` key of the setup table, which is [shown
here](https://github.com/neovim/nvim-lspconfig/blob/master/doc/server_configurations.md#rust_analyzer).
configuration. The following code will work for any checkout of rust-lang/rust (newer than Febuary 2025):

```lua
lspconfig.rust_analyzer.setup {
root_dir = function()
local default = lspconfig.rust_analyzer.config_def.default_config.root_dir()
-- the default root detection uses the cargo workspace root.
-- but for rust-lang/rust, the standard library is in its own workspace.
-- use the git root instead.
local compiler_config = vim.fs.joinpath(default, "../src/bootstrap/defaults/config.compiler.toml")
if vim.fs.basename(default) == "library" and vim.uv.fs_stat(compiler_config) then
return vim.fs.dirname(default)
end
return default
end,
on_init = function(client)
local path = client.workspace_folders[1].name
local config = vim.fs.joinpath(path, "src/etc/rust_analyzer_zed.json")
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm really curious how neovim handles the ${workspaceFolder} variable. I've searched the codebases of neovim, nvim-lspconfig, and neoconf.nvim, but haven't found anything that seems to be processing it.

if vim.uv.fs_stat(config) then
-- load rust-lang/rust settings
local file = io.open(config)
local json = vim.json.decode(file:read("*a"))
client.config.settings["rust-analyzer"] = json.lsp["rust-analyzer"].initialization_options
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The code snippet is from https://github.com/mfussenegger/nvim-dap/blob/379cf26e9c457b66a0152cd5d018418c03720d47/lua/dap.lua#L375-L402.

        local var_placeholders = {
          ['${workspaceFolder}'] = function(_)
            return vim.fn.getcwd()
          end,
        }

        local function expand_config_variables(option)
          if type(option) == "table" then
            local mt = getmetatable(option)
            local result = {}
            for k, v in pairs(option) do
              result[expand_config_variables(k)] = expand_config_variables(v)
            end
            return setmetatable(result, mt)
          end
          if type(option) ~= "string" then
            return option
          end
          local ret = option
          for key, fn in pairs(var_placeholders) do
            ret = ret:gsub(key, fn)
          end
          return ret
        end
        local options = expand_config_variables(json.lsp["rust-analyzer"].initialization_options)
        client.config.settings["rust-analyzer"] = options

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this is definitely not any part of base nvim. i am not sure why nvim-dap is trying to support this; you're welcome to add it to your config i guess but i don't think we should recommend it in the dev guide.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

(note it's also doing it wrong, the working directory is not necessarily the same as the workspace folder)

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this is definitely not any part of base nvim. i am not sure why nvim-dap is trying to support this; you're welcome to add it to your config i guess but i don't think we should recommend it in the dev guide.

I think we should at least mention this? Otherwise, some people might not understand why rustfmt and proc macros aren't working?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

(note it's also doing it wrong, the working directory is not necessarily the same as the workspace folder)

I believe this is the most commonly used. I think we just need to mention the replacement of ${workspaceFolder}, and everyone can modify this variable in their own preferred way.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think we should at least mention this? Otherwise, some people might not understand why rustfmt and proc macros aren't working?

oh i was confused, i'm sorry. you're right - the Zed file this is copying is using workspaceFolder. this is a good solution to make that work without further configuration, thank you for researching it.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I believe this is the most commonly used. I think we just need to mention the replacement of ${workspaceFolder}, and everyone can modify this variable in their own preferred way.

i think we should suggest vim.lsp.buf.list_workspace_folders()[1], not getcwd().

client.notify("workspace/didChangeConfiguration", { settings = client.config.settings })
end
return true
end
}
```

If you would like to use the build task that is described above, you may either
make your own command in your config, or you can install a plugin such as
Expand Down