simrat39 / rust-tools.nvim

Tools for better development in rust using neovim's builtin lsp
MIT License
2.17k stars 160 forks source link

Support native inlay hints #395

Closed augustocdias closed 1 year ago

augustocdias commented 1 year ago

I'm not sure if "support" is correct way to put it. I'm not sure if the inlay hints are customisable to add symbols like rust-tools enable, but in nightly now there's native inlay hints. If I enable native and from rust-tools I get duplicated hints (expected). I think rust-tools could check if native is enabled and ignore if that's the case to avoid showing duplicated.

Mathijs-Bakker commented 1 year ago

Yeah, should be an option in rust-tools config.

Mathijs-Bakker commented 1 year ago

In /after/ftplugin

I added the file: rust.vim with the following content:

lua << EOF
vim.lsp.inlay_hint(0, true)
EOF

and in rust-tool config:

inlay_hints {
 auto = false,
 ..
}

🦀

** 4 juli '23 :: updated this post for a breaking neovim api change

augustocdias commented 1 year ago

I was aware of that. I just think rust-tools should check it and enable or disable its own hints.

musjj commented 1 year ago

One thing I'm noticing with the native inlay hints is that the return type annotations is sometimes placed after the diagnostics. This means that if the diagnostics line is long enough it'll get pushed out of view.

image I think the placement depends on which one gets rendered first.

Is there a way to change this behavior?

musjj commented 1 year ago

Never mind, actually the native inlay hints are not working at all. If you think you're seeing the native inlay hints, you're probably seeing ones from this plugin.

Setting inlay_hints { auto = false } to your config will still enable rust-tools's inlay hints, not the native one. You can try running RustDisableInlayHints (a command from this plugin) to confirm this behavior.

You can switch to a vanilla lspconfig setup and run vim.lsp.inlay_hint(0, true) and you will see that the native inlay hints are not working at all. Not sure what's going on here.

EDIT: To enable it, I had to manually run vim.lsp.buf.inlay_hint(0, false), then vim.lsp.buf.inlay_hint(0, true) again. Not sure why...

latipun7 commented 1 year ago

Not sure what you are doing, @musjj . Native inlay hints do works. Setting inlay_hints = { auto = false } really disable rust-tools' inlay hint for me. I don't need to enable inlay hints manually, I use these settings: https://github.com/latipun7/dotfiles/commit/f9750042e9503eba4d6cf05ce7bb5465437bcf4f

Note: since https://github.com/neovim/neovim/commit/37079fca58f396fd866dc7b7d87a0100c17ee760 I guess vim.lsp.buf.inlay_hint() not works, you need to move it to vim.lsp.inlay_hint().

musjj commented 1 year ago

I solved the auto = false problem (I put them in the wrong table), sorry about that, kinda rushed without thinking. I'm alredy using vim.lsp.inlay_hint and my neovim version is v0.10.0-dev-606+g628f6cce8. But the inlay hints are still not enabled automatically for me. I have this in my on_attach:

on_attach = function(client, buffer)
  if client.server_capabilities.inlayHintProvider then
    vim.notify("enabling hints")
    vim.lsp.inlay_hint(buffer, true)
  end
end

The notify is there just to confirm that it's running at all. Inlay hints works perfectly fine for Lua. For Rust, I have to manually run vim.lsp.inlay_hint(0, false) and then vim.lsp.inlay_hint(0, true) after opening a file. Manually running just vim.lsp.inlay_hint(0, true) does not work. The issue occurs with both rust-tools.nvim and a vanilla lspconfig setup. I'm not sure why this is happening. Kinda hard to imagine a plugin that would interfere with this, but I might debug it a bit more later.

EDIT: It seems that the inlay hints will only get rendered, after entering insert mode and inputting a keystroke for the first time. So far this only happens with Rust, but not other languages.

musjj commented 1 year ago

Made a minimal reproduction:

vim.api.nvim_create_autocmd("FileType", {
  pattern = "rust",
  callback = function(args)
    local path = vim.fs.dirname(vim.api.nvim_buf_get_name(args.buf))
    local match = vim.fs.find("Cargo.toml", { path = path, upward = true })[1]
    if match then
      vim.lsp.start {
        name = "rust_analyzer",
        cmd = { "rust-analyzer" },
        root_dir = vim.fs.dirname(match),
        on_attach = function(client, bufnr) vim.lsp.inlay_hint(bufnr, true) end,
      }
    end
  end,
})

Run it like this: nvim -u repro.lua src/main.rs

The hints will not show up until you start typing. I suspect that this is an upstream issue.

wohckcin commented 1 year ago

I solved the auto = false problem (I put them in the wrong table), sorry about that, kinda rushed without thinking. I'm alredy using vim.lsp.inlay_hint and my neovim version is v0.10.0-dev-606+g628f6cce8. But the inlay hints are still not enabled automatically for me. I have this in my on_attach:

on_attach = function(client, buffer)
  if client.server_capabilities.inlayHintProvider then
    vim.notify("enabling hints")
    vim.lsp.inlay_hint(buffer, true)
  end
end

The notify is there just to confirm that it's running at all. Inlay hints works perfectly fine for Lua. For Rust, I have to manually run vim.lsp.inlay_hint(0, false) and then vim.lsp.inlay_hint(0, true) after opening a file. Manually running just vim.lsp.inlay_hint(0, true) does not work. The issue occurs with both rust-tools.nvim and a vanilla lspconfig setup. I'm not sure why this is happening. Kinda hard to imagine a plugin that would interfere with this, but I might debug it a bit more later.

EDIT: It seems that the inlay hints will only get rendered, after entering insert mode and inputting a keystroke for the first time. So far this only happens with Rust, but not other languages.

@musjj can confirm your issue. I am experiencing the same problem.

Mathijs-Bakker commented 1 year ago

EDIT: It seems that the inlay hints will only get rendered, after entering insert mode and inputting a keystroke for the first time. So far this only happens with Rust, but not other languages.

I don't think this is rust-tools related but typical a rust-analyzer (RA) behavior.

Note: It's a common 'issue' with RA that it is slow analyzing your Rust crate(s) on start up. It takes some time to scan all directories for the root paths of the current Rust project and its dependencies.

In my case everything behaves as intended. It depends on machine and project, but the average time it takes for RA to automatically show the inlay help and clippy info, is about 8 seconds.

musjj commented 1 year ago

Yeah, it's not really a rust-tools issue, it's probably an upstream issue. But the problem is not that it's slow, the inlay hints will never show up until you start typing. You can test the reproduction config above on a small Rust project, wait until rust-analyzer is done without typing anything, and the hints will still not show up.

I'm also experiencing a bug where lines gets virtually duplicated when lines containing hints gets wrapped (if you have set wrap). Still don't have solid reproduction for this one. And of course there's also that backspace issue that has been reported in the neovim repro.

In general, native inlay hints is still in a pretty rough state right now (understandable, since it's a nightly feature). I think I'll stick with rust-tools's hints for now.

simrat39 commented 1 year ago

https://github.com/simrat39/rust-tools.nvim/blob/master/lua/rust-tools/server_status.lua#L7-L9

We enable inlay hints when the server is done processing the codebase, that's probably why the native inlay hints are slow