lsp: Add `detail` to completion resolvable properties (#45985)
Shuhei Kadowaki
created
Previously, `detail` was not included in resolvable properties, which
prevented LSP-compliant servers from lazily resolving it.
In relation to this, I also investigated vtsls issues:
- https://github.com/yioneko/vtsls/issues/213
- https://github.com/zed-industries/zed/pull/21521
My conclusion is that regardless of whether Zed registers `detail` in
resolvable properties, vtsls always lazily resolves `detail`. However, I
understand that Zed's `resolve_completions` has been improved to handle
such "misbehaving" servers gracefully already, so I expect that adding
`detail` to resolvable properties will not cause any issues.
In fact, since Zed can lazy update all properties of completion items,
it might be appropriate to include all properties as resolvable except
for `label` (which is explicitly tested for consistency) and `data`
(which is used for resolution itself once).
However, since I'm uncertain if this is entirely correct, this commit
only adds `detail` to resolvable properties, as it was required to be
supported by LSP clients up to version 3.16.
Closes #ISSUE
Release Notes:
- N/A
@@ -761,6 +761,7 @@ impl LanguageServer {
properties: vec![
"additionalTextEdits".to_string(),
"command".to_string(),
+ "detail".to_string(),
"documentation".to_string(),
// NB: Do not have this resolved, otherwise Zed becomes slow to complete things
// "textEdit".to_string(),
@@ -6537,8 +6537,9 @@ impl LspStore {
let mut new_label = match completion_item {
Some(completion_item) => {
- // NB: Zed does not have `details` inside the completion resolve capabilities, but certain language servers violate the spec and do not return `details` immediately, e.g. https://github.com/yioneko/vtsls/issues/213- // So we have to update the label here anyway...
+ // Some language servers always return `detail` lazily via resolve, regardless of
+ // the resolvable properties Zed advertises. Regenerate labels here to handle this.
+ // See: https://github.com/yioneko/vtsls/issues/213
let language = snapshot.language();
match language {
Some(language) => {