diff options
| author | bors <bors@rust-lang.org> | 2022-11-29 18:37:00 +0000 |
|---|---|---|
| committer | bors <bors@rust-lang.org> | 2022-11-29 18:37:00 +0000 |
| commit | 398a71affb05aeeea1991044ec9ca1229e68f0f3 (patch) | |
| tree | 10b95b31f435de1ecd165bb885abdfa72a2254af | |
| parent | e69fb5e9ef1051eb405865ad4aad7cc5a02877a2 (diff) | |
| parent | 32f59cf01de639d0b23753687f5fb5b08c0758c0 (diff) | |
| download | rust-398a71affb05aeeea1991044ec9ca1229e68f0f3.tar.gz rust-398a71affb05aeeea1991044ec9ca1229e68f0f3.zip | |
Auto merge of #13697 - jonas-schievink:version-inlay-hint-resolve-data, r=jonas-schievink
internal: Version the inlay hint resolve data cc https://github.com/rust-lang/rust-analyzer/issues/13657 cc https://github.com/rust-lang/rust-analyzer/issues/13372 cc https://github.com/rust-lang/rust-analyzer/issues/13170 This will make us log an error and return the unmodified inlay hints when the client attempts to resolve inlay hints in a file that has since been modified.
| -rw-r--r-- | crates/rust-analyzer/src/from_proto.rs | 10 | ||||
| -rw-r--r-- | crates/rust-analyzer/src/handlers.rs | 22 | ||||
| -rw-r--r-- | crates/rust-analyzer/src/lsp_ext.rs | 4 | ||||
| -rw-r--r-- | crates/rust-analyzer/src/to_proto.rs | 10 | ||||
| -rw-r--r-- | docs/dev/lsp-extensions.md | 2 |
5 files changed, 40 insertions, 8 deletions
diff --git a/crates/rust-analyzer/src/from_proto.rs b/crates/rust-analyzer/src/from_proto.rs index dd433b0f4d3..4e7095b3ce3 100644 --- a/crates/rust-analyzer/src/from_proto.rs +++ b/crates/rust-analyzer/src/from_proto.rs @@ -67,7 +67,15 @@ pub(crate) fn file_range( text_document_identifier: lsp_types::TextDocumentIdentifier, range: lsp_types::Range, ) -> Result<FileRange> { - let file_id = file_id(snap, &text_document_identifier.uri)?; + file_range_uri(snap, &text_document_identifier.uri, range) +} + +pub(crate) fn file_range_uri( + snap: &GlobalStateSnapshot, + document: &lsp_types::Url, + range: lsp_types::Range, +) -> Result<FileRange> { + let file_id = file_id(snap, document)?; let line_index = snap.file_line_index(file_id)?; let range = text_range(&line_index, range)?; Ok(FileRange { file_id, range }) diff --git a/crates/rust-analyzer/src/handlers.rs b/crates/rust-analyzer/src/handlers.rs index 4f318f39de5..1604a02fb13 100644 --- a/crates/rust-analyzer/src/handlers.rs +++ b/crates/rust-analyzer/src/handlers.rs @@ -29,6 +29,7 @@ use project_model::{ManifestPath, ProjectWorkspace, TargetKind}; use serde_json::json; use stdx::{format_to, never}; use syntax::{algo, ast, AstNode, TextRange, TextSize}; +use tracing::error; use vfs::AbsPathBuf; use crate::{ @@ -1372,9 +1373,26 @@ pub(crate) fn handle_inlay_hints_resolve( let resolve_data: lsp_ext::InlayHintResolveData = serde_json::from_value(data)?; - let file_range = from_proto::file_range( + match snap.url_file_version(&resolve_data.text_document.uri) { + Some(version) if version == resolve_data.text_document.version => {} + Some(version) => { + error!( + "attempted inlayHints/resolve of '{}' at version {} while server version is {}", + resolve_data.text_document.uri, resolve_data.text_document.version, version, + ); + return Ok(hint); + } + None => { + error!( + "attempted inlayHints/resolve of unknown file '{}' at version {}", + resolve_data.text_document.uri, resolve_data.text_document.version, + ); + return Ok(hint); + } + } + let file_range = from_proto::file_range_uri( &snap, - resolve_data.text_document, + &resolve_data.text_document.uri, match resolve_data.position { PositionOrRange::Position(pos) => Range::new(pos, pos), PositionOrRange::Range(range) => range, diff --git a/crates/rust-analyzer/src/lsp_ext.rs b/crates/rust-analyzer/src/lsp_ext.rs index 8cc5648f3ce..a1df0b6d7dd 100644 --- a/crates/rust-analyzer/src/lsp_ext.rs +++ b/crates/rust-analyzer/src/lsp_ext.rs @@ -3,11 +3,11 @@ use std::{collections::HashMap, path::PathBuf}; use lsp_types::request::Request; -use lsp_types::PositionEncodingKind; use lsp_types::{ notification::Notification, CodeActionKind, DocumentOnTypeFormattingParams, PartialResultParams, Position, Range, TextDocumentIdentifier, WorkDoneProgressParams, }; +use lsp_types::{PositionEncodingKind, VersionedTextDocumentIdentifier}; use serde::{Deserialize, Serialize}; pub enum AnalyzerStatus {} @@ -550,7 +550,7 @@ pub struct CompletionResolveData { #[derive(Debug, Serialize, Deserialize)] pub struct InlayHintResolveData { - pub text_document: TextDocumentIdentifier, + pub text_document: VersionedTextDocumentIdentifier, pub position: PositionOrRange, } diff --git a/crates/rust-analyzer/src/to_proto.rs b/crates/rust-analyzer/src/to_proto.rs index d1f805af1d4..3ce24bdd14f 100644 --- a/crates/rust-analyzer/src/to_proto.rs +++ b/crates/rust-analyzer/src/to_proto.rs @@ -492,7 +492,10 @@ pub(crate) fn inlay_hint( let uri = url(snap, file_id); let line_index = snap.file_line_index(file_id).ok()?; - let text_document = lsp_types::TextDocumentIdentifier { uri }; + let text_document = lsp_types::VersionedTextDocumentIdentifier { + version: snap.url_file_version(&uri)?, + uri, + }; to_value(lsp_ext::InlayHintResolveData { text_document, position: lsp_ext::PositionOrRange::Position(position(&line_index, offset)), @@ -501,7 +504,10 @@ pub(crate) fn inlay_hint( } Some(ide::InlayTooltip::HoverRanged(file_id, text_range)) => { let uri = url(snap, file_id); - let text_document = lsp_types::TextDocumentIdentifier { uri }; + let text_document = lsp_types::VersionedTextDocumentIdentifier { + version: snap.url_file_version(&uri)?, + uri, + }; let line_index = snap.file_line_index(file_id).ok()?; to_value(lsp_ext::InlayHintResolveData { text_document, diff --git a/docs/dev/lsp-extensions.md b/docs/dev/lsp-extensions.md index fe316fcae9b..5aced035d52 100644 --- a/docs/dev/lsp-extensions.md +++ b/docs/dev/lsp-extensions.md @@ -1,5 +1,5 @@ <!--- -lsp_ext.rs hash: 62068e53ac202dc8 +lsp_ext.rs hash: 61fe425627f9baaa If you need to change the above hash to make the test pass, please check if you need to adjust this doc as well and ping this issue: |
