summaryrefslogtreecommitdiff
path: root/test_util/src
diff options
context:
space:
mode:
Diffstat (limited to 'test_util/src')
-rw-r--r--test_util/src/lsp.rs139
1 files changed, 49 insertions, 90 deletions
diff --git a/test_util/src/lsp.rs b/test_util/src/lsp.rs
index 5fbca7f35..a7061543f 100644
--- a/test_util/src/lsp.rs
+++ b/test_util/src/lsp.rs
@@ -87,12 +87,6 @@ impl<'a> From<&'a [u8]> for LspMessage {
}
}
-#[derive(Debug, Deserialize)]
-struct DiagnosticBatchNotificationParams {
- batch_index: usize,
- messages_len: usize,
-}
-
fn read_message<R>(reader: &mut R) -> Result<Option<Vec<u8>>>
where
R: io::Read + io::BufRead,
@@ -180,25 +174,6 @@ impl LspStdoutReader {
cvar.wait(&mut msg_queue);
}
}
-
- pub fn read_latest_message<R>(
- &mut self,
- mut get_match: impl FnMut(&LspMessage) -> Option<R>,
- ) -> R {
- let (msg_queue, cvar) = &*self.pending_messages;
- let mut msg_queue = msg_queue.lock();
- loop {
- for i in (0..msg_queue.len()).rev() {
- let msg = &msg_queue[i];
- if let Some(result) = get_match(msg) {
- let msg = msg_queue.remove(i);
- self.read_messages.push(msg);
- return result;
- }
- }
- cvar.wait(&mut msg_queue);
- }
- }
}
pub struct InitializeParamsBuilder {
@@ -510,8 +485,6 @@ impl LspClientBuilder {
command
.env("DENO_DIR", deno_dir.path())
.env("NPM_CONFIG_REGISTRY", npm_registry_url())
- // turn on diagnostic synchronization communication
- .env("DENO_DONT_USE_INTERNAL_LSP_DIAGNOSTIC_SYNC_FLAG", "1")
.arg("lsp")
.stdin(Stdio::piped())
.stdout(Stdio::piped());
@@ -537,6 +510,7 @@ impl LspClientBuilder {
.unwrap_or_else(|| TestContextBuilder::new().build()),
writer,
deno_dir,
+ diagnosable_open_file_count: 0,
})
}
}
@@ -549,6 +523,7 @@ pub struct LspClient {
writer: io::BufWriter<ChildStdin>,
deno_dir: TempDir,
context: TestContext,
+ diagnosable_open_file_count: usize,
}
impl Drop for LspClient {
@@ -634,6 +609,20 @@ impl LspClient {
}
pub fn did_open_raw(&mut self, params: Value) {
+ let text_doc = params
+ .as_object()
+ .unwrap()
+ .get("textDocument")
+ .unwrap()
+ .as_object()
+ .unwrap();
+ if matches!(
+ text_doc.get("languageId").unwrap().as_str().unwrap(),
+ "typescript" | "javascript"
+ ) {
+ self.diagnosable_open_file_count += 1;
+ }
+
self.write_notification("textDocument/didOpen", params);
}
@@ -643,46 +632,11 @@ impl LspClient {
self.write_response(id, result);
}
- fn get_latest_diagnostic_batch_index(&mut self) -> usize {
- let result = self
- .write_request("deno/internalLatestDiagnosticBatchIndex", json!(null));
- result.as_u64().unwrap() as usize
- }
-
- /// Reads the latest diagnostics. It's assumed that
pub fn read_diagnostics(&mut self) -> CollectedDiagnostics {
- // ask the server what the latest diagnostic batch index is
- let latest_diagnostic_batch_index =
- self.get_latest_diagnostic_batch_index();
-
- // now wait for three (deno, lint, and typescript diagnostics) batch
- // notification messages for that index
- let mut read = 0;
- let mut total_messages_len = 0;
- while read < 3 {
- let (method, response) =
- self.read_notification::<DiagnosticBatchNotificationParams>();
- assert_eq!(method, "deno/internalTestDiagnosticBatch");
- let response = response.unwrap();
- if response.batch_index == latest_diagnostic_batch_index {
- read += 1;
- total_messages_len += response.messages_len;
- }
+ let mut all_diagnostics = Vec::new();
+ for _ in 0..self.diagnosable_open_file_count {
+ all_diagnostics.extend(read_diagnostics(self).0);
}
-
- // now read the latest diagnostic messages
- let mut all_diagnostics = Vec::with_capacity(total_messages_len);
- let mut seen_files = HashSet::new();
- for _ in 0..total_messages_len {
- let (method, response) =
- self.read_latest_notification::<lsp::PublishDiagnosticsParams>();
- assert_eq!(method, "textDocument/publishDiagnostics");
- let response = response.unwrap();
- if seen_files.insert(response.uri.to_string()) {
- all_diagnostics.push(response);
- }
- }
-
CollectedDiagnostics(all_diagnostics)
}
@@ -714,19 +668,6 @@ impl LspClient {
})
}
- pub fn read_latest_notification<R>(&mut self) -> (String, Option<R>)
- where
- R: de::DeserializeOwned,
- {
- self.reader.read_latest_message(|msg| match msg {
- LspMessage::Notification(method, maybe_params) => {
- let params = serde_json::from_value(maybe_params.clone()?).ok()?;
- Some((method.to_string(), params))
- }
- _ => None,
- })
- }
-
pub fn read_notification_with_method<R>(
&mut self,
expected_method: &str,
@@ -878,29 +819,35 @@ impl LspClient {
}
#[derive(Debug, Clone)]
-pub struct CollectedDiagnostics(Vec<lsp::PublishDiagnosticsParams>);
+pub struct CollectedDiagnostics(pub Vec<lsp::PublishDiagnosticsParams>);
impl CollectedDiagnostics {
/// Gets the diagnostics that the editor will see after all the publishes.
- pub fn all(&self) -> Vec<lsp::Diagnostic> {
+ pub fn viewed(&self) -> Vec<lsp::Diagnostic> {
self
- .all_messages()
+ .viewed_messages()
.into_iter()
.flat_map(|m| m.diagnostics)
.collect()
}
/// Gets the messages that the editor will see after all the publishes.
- pub fn all_messages(&self) -> Vec<lsp::PublishDiagnosticsParams> {
- self.0.clone()
+ pub fn viewed_messages(&self) -> Vec<lsp::PublishDiagnosticsParams> {
+ // go over the publishes in reverse order in order to get
+ // the final messages that will be shown in the editor
+ let mut messages = Vec::new();
+ let mut had_specifier = HashSet::new();
+ for message in self.0.iter().rev() {
+ if had_specifier.insert(message.uri.clone()) {
+ messages.insert(0, message.clone());
+ }
+ }
+ messages
}
- pub fn messages_with_source(
- &self,
- source: &str,
- ) -> lsp::PublishDiagnosticsParams {
+ pub fn with_source(&self, source: &str) -> lsp::PublishDiagnosticsParams {
self
- .all_messages()
+ .viewed_messages()
.iter()
.find(|p| {
p.diagnostics
@@ -911,14 +858,14 @@ impl CollectedDiagnostics {
.unwrap()
}
- pub fn messages_with_file_and_source(
+ pub fn with_file_and_source(
&self,
specifier: &str,
source: &str,
) -> lsp::PublishDiagnosticsParams {
let specifier = Url::parse(specifier).unwrap();
self
- .all_messages()
+ .viewed_messages()
.iter()
.find(|p| {
p.uri == specifier
@@ -932,6 +879,18 @@ impl CollectedDiagnostics {
}
}
+fn read_diagnostics(client: &mut LspClient) -> CollectedDiagnostics {
+ // diagnostics come in batches of three unless they're cancelled
+ let mut diagnostics = vec![];
+ for _ in 0..3 {
+ let (method, response) =
+ client.read_notification::<lsp::PublishDiagnosticsParams>();
+ assert_eq!(method, "textDocument/publishDiagnostics");
+ diagnostics.push(response.unwrap());
+ }
+ CollectedDiagnostics(diagnostics)
+}
+
#[cfg(test)]
mod tests {
use super::*;