From 9d344570b4e5aaa79506c5c0a0c1847f70135efe Mon Sep 17 00:00:00 2001 From: Myriad-Dreamin <35292584+Myriad-Dreamin@users.noreply.github.com> Date: Thu, 14 Mar 2024 20:37:14 +0800 Subject: [PATCH] dev: borrow the document state inside of compiler (#33) --- crates/tinymist-query/src/completion.rs | 4 ++-- crates/tinymist-query/src/hover.rs | 6 +++-- crates/tinymist-query/src/lib.rs | 10 ++++++++ crates/tinymist-query/src/prelude.rs | 3 ++- crates/tinymist/src/actor/compile.rs | 7 +----- crates/tinymist/src/actor/typst.rs | 31 ++++++++++++------------- 6 files changed, 34 insertions(+), 27 deletions(-) diff --git a/crates/tinymist-query/src/completion.rs b/crates/tinymist-query/src/completion.rs index 3e648a48..37837394 100644 --- a/crates/tinymist-query/src/completion.rs +++ b/crates/tinymist-query/src/completion.rs @@ -11,10 +11,10 @@ impl CompletionRequest { pub fn request( self, world: &TypstSystemWorld, - doc: Option>, + doc: Option, position_encoding: PositionEncoding, ) -> Option { - let doc = doc.as_deref(); + let doc = doc.as_ref().map(|doc| doc.document.as_ref()); let source = get_suitable_source_in_workspace(world, &self.path).ok()?; let cursor = lsp_to_typst::position(self.position, position_encoding, &source)?; diff --git a/crates/tinymist-query/src/hover.rs b/crates/tinymist-query/src/hover.rs index 6fd81a33..96b86617 100644 --- a/crates/tinymist-query/src/hover.rs +++ b/crates/tinymist-query/src/hover.rs @@ -10,15 +10,17 @@ impl HoverRequest { pub fn request( self, world: &TypstSystemWorld, - doc: Option>, + doc: Option, position_encoding: PositionEncoding, ) -> Option { + let doc = doc.as_ref().map(|doc| doc.document.as_ref()); + let source = get_suitable_source_in_workspace(world, &self.path).ok()?; let offset = lsp_to_typst::position(self.position, position_encoding, &source)?; // the typst's cursor is 1-based, so we need to add 1 to the offset let cursor = offset + 1; - let typst_tooltip = typst_ide::tooltip(world, doc.as_deref(), &source, cursor)?; + let typst_tooltip = typst_ide::tooltip(world, doc, &source, cursor)?; let ast_node = LinkedNode::new(source.root()).leaf_at(cursor)?; let range = typst_to_lsp::range(ast_node.range(), &source, position_encoding); diff --git a/crates/tinymist-query/src/lib.rs b/crates/tinymist-query/src/lib.rs index 0c366533..44a78274 100644 --- a/crates/tinymist-query/src/lib.rs +++ b/crates/tinymist-query/src/lib.rs @@ -3,6 +3,10 @@ pub mod analysis; pub(crate) mod diagnostics; +use std::sync::Arc; + +use typst_ts_core::TypstDocument; + pub use diagnostics::*; pub(crate) mod signature_help; pub use signature_help::*; @@ -40,6 +44,12 @@ pub use lsp_typst_boundary::*; mod prelude; +#[derive(Debug, Clone)] +pub struct VersionedDocument { + pub version: usize, + pub document: Arc, +} + mod polymorphic { use super::prelude::*; use super::*; diff --git a/crates/tinymist-query/src/prelude.rs b/crates/tinymist-query/src/prelude.rs index ca45233a..ba98b1e4 100644 --- a/crates/tinymist-query/src/prelude.rs +++ b/crates/tinymist-query/src/prelude.rs @@ -26,13 +26,14 @@ pub use typst::syntax::{ pub use typst::World; use typst_ts_compiler::service::WorkspaceProvider; pub use typst_ts_compiler::TypstSystemWorld; -pub use typst_ts_core::{TypstDocument, TypstFileId}; +pub use typst_ts_core::TypstFileId; pub use crate::analysis::analyze_expr; pub use crate::lsp_typst_boundary::{ lsp_to_typst, typst_to_lsp, LspDiagnostic, LspRange, LspSeverity, PositionEncoding, TypstDiagnostic, TypstSeverity, TypstSpan, }; +pub use crate::VersionedDocument; pub fn get_suitable_source_in_workspace(w: &TypstSystemWorld, p: &Path) -> FileResult { // todo: source in packages diff --git a/crates/tinymist/src/actor/compile.rs b/crates/tinymist/src/actor/compile.rs index 6fa8eb7c..09a6c704 100644 --- a/crates/tinymist/src/actor/compile.rs +++ b/crates/tinymist/src/actor/compile.rs @@ -8,6 +8,7 @@ use std::{ }; use serde::Serialize; +use tinymist_query::VersionedDocument; use tokio::sync::{mpsc, oneshot}; use typst::{ layout::{Frame, FrameItem, Point, Position}, @@ -34,12 +35,6 @@ use typst_ts_compiler::service::{ use crate::{task::BorrowTask, utils}; -#[derive(Debug, Clone)] -pub struct VersionedDocument { - pub version: usize, - pub document: Arc, -} - /// Interrupts for external sources enum ExternalInterrupt { /// Compile anyway. diff --git a/crates/tinymist/src/actor/typst.rs b/crates/tinymist/src/actor/typst.rs index 17d674c3..03762fde 100644 --- a/crates/tinymist/src/actor/typst.rs +++ b/crates/tinymist/src/actor/typst.rs @@ -11,7 +11,7 @@ use once_cell::sync::OnceCell; use parking_lot::Mutex; use tinymist_query::{ CompilerQueryRequest, CompilerQueryResponse, DiagnosticsMap, FoldRequestFeature, - OnExportRequest, OnSaveExportRequest, PositionEncoding, + OnExportRequest, OnSaveExportRequest, PositionEncoding, VersionedDocument, }; use tokio::sync::{broadcast, mpsc, oneshot, watch}; use typst::{ @@ -88,15 +88,13 @@ pub fn create_server( let (root_tx, root_rx) = oneshot::channel(); - let handler = CompileHandler { - result: Arc::new(SyncMutex::new(Err(CompileStatus::Compiling))), - inner: Arc::new(SyncMutex::new(None)), - }; - let inner = Deferred::new({ let current_runtime = tokio::runtime::Handle::current(); + let handler = CompileHandler { + inner: Arc::new(SyncMutex::new(None)), + }; + let diag_group = diag_group.clone(); - let handler = handler.clone(); let entry = entry.clone(); let render_tx = render_tx.clone(); @@ -170,7 +168,6 @@ pub fn create_server( root, entry, pos_encoding, - handler, inner, render_tx, ) @@ -192,9 +189,8 @@ impl<'a> fmt::Debug for ShowOpts<'a> { macro_rules! query_state { ($self:ident, $method:ident, $req:expr) => {{ - let doc = $self.handler.result.lock().unwrap().clone().ok(); let enc = $self.position_encoding; - let res = $self.steal_world(move |w| $req.request(w, doc, enc)); + let res = $self.steal_state(move |w, doc| $req.request(w, doc, enc)); res.map(CompilerQueryResponse::$method) }}; } @@ -209,7 +205,6 @@ macro_rules! query_world { #[derive(Clone)] pub struct CompileHandler { - result: Arc, CompileStatus>>>, inner: Arc>>, } @@ -222,8 +217,6 @@ impl CompilationHandle for CompileHandler { } fn notify_compile(&self, result: Result, CompileStatus>) { - *self.result.lock().unwrap() = result.clone(); - let inner = self.inner.lock().unwrap(); if let Some(inner) = inner.as_ref() { inner.notify_compile(result.clone()); @@ -370,7 +363,6 @@ impl, H> Reporter { pub struct CompileActor { diag_group: String, position_encoding: PositionEncoding, - handler: CompileHandler, root_tx: Mutex>>>, root: OnceCell>, entry: Arc>>, @@ -386,7 +378,6 @@ impl CompileActor { root: Option, entry: Option, position_encoding: PositionEncoding, - handler: CompileHandler, inner: Deferred>, render_tx: broadcast::Sender, ) -> Self { @@ -398,7 +389,6 @@ impl CompileActor { None => OnceCell::new(), }, position_encoding, - handler, entry: Arc::new(Mutex::new(entry)), inner, render_tx, @@ -729,6 +719,15 @@ impl CompileActor { Ok(()) } + fn steal_state( + &self, + f: impl FnOnce(&TypstSystemWorld, Option) -> T + Send + Sync + 'static, + ) -> anyhow::Result { + let fut = self.steal(move |compiler| f(compiler.compiler.world(), compiler.doc())); + + Ok(fut?) + } + fn steal_world( &self, f: impl FnOnce(&TypstSystemWorld) -> T + Send + Sync + 'static,