Use Transaction instead of ProjectTransaction
Co-Authored-By: Antonio Scandurra <antonio@zed.dev>
This commit is contained in:
parent
aa58d0fd77
commit
e2ff829f98
6 changed files with 51 additions and 78 deletions
|
@ -7444,18 +7444,11 @@ async fn test_on_input_format_from_host_to_guest(
|
||||||
|
|
||||||
let fake_language_server = fake_language_servers.next().await.unwrap();
|
let fake_language_server = fake_language_servers.next().await.unwrap();
|
||||||
cx_b.foreground().run_until_parked();
|
cx_b.foreground().run_until_parked();
|
||||||
// Type a on type formatting trigger character as the guest.
|
|
||||||
editor_a.update(cx_a, |editor, cx| {
|
|
||||||
editor.change_selections(None, cx, |s| s.select_ranges([13..13]));
|
|
||||||
editor.handle_input(">", cx);
|
|
||||||
cx.focus(&editor_a);
|
|
||||||
});
|
|
||||||
|
|
||||||
// Receive an OnTypeFormatting request as the host's language server.
|
// Receive an OnTypeFormatting request as the host's language server.
|
||||||
// Return some formattings from the host's language server.
|
// Return some formattings from the host's language server.
|
||||||
cx_b.foreground().start_waiting();
|
fake_language_server.handle_request::<lsp::request::OnTypeFormatting, _, _>(
|
||||||
fake_language_server
|
|params, _| async move {
|
||||||
.handle_request::<lsp::request::OnTypeFormatting, _, _>(|params, _| async move {
|
|
||||||
assert_eq!(
|
assert_eq!(
|
||||||
params.text_document_position.text_document.uri,
|
params.text_document_position.text_document.uri,
|
||||||
lsp::Url::from_file_path("/a/main.rs").unwrap(),
|
lsp::Url::from_file_path("/a/main.rs").unwrap(),
|
||||||
|
@ -7469,18 +7462,27 @@ async fn test_on_input_format_from_host_to_guest(
|
||||||
new_text: "~<".to_string(),
|
new_text: "~<".to_string(),
|
||||||
range: lsp::Range::new(lsp::Position::new(0, 14), lsp::Position::new(0, 14)),
|
range: lsp::Range::new(lsp::Position::new(0, 14), lsp::Position::new(0, 14)),
|
||||||
}]))
|
}]))
|
||||||
})
|
},
|
||||||
.next()
|
);
|
||||||
.await
|
// .next()
|
||||||
.unwrap();
|
// .await
|
||||||
cx_b.foreground().finish_waiting();
|
// .unwrap();
|
||||||
|
|
||||||
// Open the buffer on the guest and see that the formattings worked
|
// Open the buffer on the guest and see that the formattings worked
|
||||||
let buffer_b = project_b
|
let buffer_b = project_b
|
||||||
.update(cx_b, |p, cx| p.open_buffer((worktree_id, "main.rs"), cx))
|
.update(cx_b, |p, cx| p.open_buffer((worktree_id, "main.rs"), cx))
|
||||||
.await
|
.await
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
|
||||||
|
// Type a on type formatting trigger character as the guest.
|
||||||
|
editor_a.update(cx_a, |editor, cx| {
|
||||||
|
cx.focus(&editor_a);
|
||||||
|
editor.change_selections(None, cx, |s| s.select_ranges([13..13]));
|
||||||
|
editor.handle_input(">", cx);
|
||||||
|
});
|
||||||
|
|
||||||
cx_b.foreground().run_until_parked();
|
cx_b.foreground().run_until_parked();
|
||||||
|
|
||||||
buffer_b.read_with(cx_b, |buffer, _| {
|
buffer_b.read_with(cx_b, |buffer, _| {
|
||||||
assert_eq!(buffer.text(), "fn main() { a>~< }")
|
assert_eq!(buffer.text(), "fn main() { a>~< }")
|
||||||
});
|
});
|
||||||
|
|
|
@ -2518,8 +2518,6 @@ impl Editor {
|
||||||
return None;
|
return None;
|
||||||
}
|
}
|
||||||
|
|
||||||
let transaction_title = format!("OnTypeFormatting after {input}");
|
|
||||||
let workspace = self.workspace(cx)?;
|
|
||||||
let project = self.project.as_ref()?;
|
let project = self.project.as_ref()?;
|
||||||
let position = self.selections.newest_anchor().head();
|
let position = self.selections.newest_anchor().head();
|
||||||
let (buffer, buffer_position) = self
|
let (buffer, buffer_position) = self
|
||||||
|
@ -2527,20 +2525,11 @@ impl Editor {
|
||||||
.read(cx)
|
.read(cx)
|
||||||
.text_anchor_for_position(position.clone(), cx)?;
|
.text_anchor_for_position(position.clone(), cx)?;
|
||||||
let on_type_formatting = project.update(cx, |project, cx| {
|
let on_type_formatting = project.update(cx, |project, cx| {
|
||||||
project.on_type_format(buffer, buffer_position, input, cx)
|
project.on_type_format(buffer, buffer_position, input, true, cx)
|
||||||
});
|
});
|
||||||
|
|
||||||
Some(cx.spawn(|editor, mut cx| async move {
|
Some(cx.spawn(|editor, mut cx| async move {
|
||||||
let project_transaction = on_type_formatting.await?;
|
on_type_formatting.await?;
|
||||||
Self::open_project_transaction(
|
|
||||||
&editor,
|
|
||||||
workspace.downgrade(),
|
|
||||||
project_transaction,
|
|
||||||
transaction_title,
|
|
||||||
cx.clone(),
|
|
||||||
)
|
|
||||||
.await?;
|
|
||||||
|
|
||||||
editor.update(&mut cx, |editor, cx| {
|
editor.update(&mut cx, |editor, cx| {
|
||||||
editor.refresh_document_highlights(cx);
|
editor.refresh_document_highlights(cx);
|
||||||
})?;
|
})?;
|
||||||
|
|
|
@ -12,7 +12,7 @@ use language::{
|
||||||
point_from_lsp, point_to_lsp,
|
point_from_lsp, point_to_lsp,
|
||||||
proto::{deserialize_anchor, deserialize_version, serialize_anchor, serialize_version},
|
proto::{deserialize_anchor, deserialize_version, serialize_anchor, serialize_version},
|
||||||
range_from_lsp, range_to_lsp, Anchor, Bias, Buffer, CachedLspAdapter, CharKind, CodeAction,
|
range_from_lsp, range_to_lsp, Anchor, Bias, Buffer, CachedLspAdapter, CharKind, CodeAction,
|
||||||
Completion, OffsetRangeExt, PointUtf16, ToOffset, ToPointUtf16, Unclipped,
|
Completion, OffsetRangeExt, PointUtf16, ToOffset, ToPointUtf16, Transaction, Unclipped,
|
||||||
};
|
};
|
||||||
use lsp::{DocumentHighlightKind, LanguageServer, LanguageServerId, ServerCapabilities};
|
use lsp::{DocumentHighlightKind, LanguageServer, LanguageServerId, ServerCapabilities};
|
||||||
use std::{cmp::Reverse, ops::Range, path::Path, sync::Arc};
|
use std::{cmp::Reverse, ops::Range, path::Path, sync::Arc};
|
||||||
|
@ -1628,7 +1628,7 @@ impl LspCommand for GetCodeActions {
|
||||||
|
|
||||||
#[async_trait(?Send)]
|
#[async_trait(?Send)]
|
||||||
impl LspCommand for OnTypeFormatting {
|
impl LspCommand for OnTypeFormatting {
|
||||||
type Response = ProjectTransaction;
|
type Response = Option<Transaction>;
|
||||||
type LspRequest = lsp::request::OnTypeFormatting;
|
type LspRequest = lsp::request::OnTypeFormatting;
|
||||||
type ProtoRequest = proto::OnTypeFormatting;
|
type ProtoRequest = proto::OnTypeFormatting;
|
||||||
|
|
||||||
|
@ -1668,7 +1668,7 @@ impl LspCommand for OnTypeFormatting {
|
||||||
buffer: ModelHandle<Buffer>,
|
buffer: ModelHandle<Buffer>,
|
||||||
server_id: LanguageServerId,
|
server_id: LanguageServerId,
|
||||||
mut cx: AsyncAppContext,
|
mut cx: AsyncAppContext,
|
||||||
) -> Result<ProjectTransaction> {
|
) -> Result<Option<Transaction>> {
|
||||||
if let Some(edits) = message {
|
if let Some(edits) = message {
|
||||||
let (lsp_adapter, lsp_server) =
|
let (lsp_adapter, lsp_server) =
|
||||||
language_server_for_buffer(&project, &buffer, server_id, &mut cx)?;
|
language_server_for_buffer(&project, &buffer, server_id, &mut cx)?;
|
||||||
|
@ -1683,7 +1683,7 @@ impl LspCommand for OnTypeFormatting {
|
||||||
)
|
)
|
||||||
.await
|
.await
|
||||||
} else {
|
} else {
|
||||||
Ok(ProjectTransaction::default())
|
Ok(None)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1729,33 +1729,27 @@ impl LspCommand for OnTypeFormatting {
|
||||||
}
|
}
|
||||||
|
|
||||||
fn response_to_proto(
|
fn response_to_proto(
|
||||||
response: ProjectTransaction,
|
response: Option<Transaction>,
|
||||||
project: &mut Project,
|
_: &mut Project,
|
||||||
peer_id: PeerId,
|
_: PeerId,
|
||||||
_: &clock::Global,
|
_: &clock::Global,
|
||||||
cx: &mut AppContext,
|
_: &mut AppContext,
|
||||||
) -> proto::OnTypeFormattingResponse {
|
) -> proto::OnTypeFormattingResponse {
|
||||||
let transaction = project.serialize_project_transaction_for_peer(response, peer_id, cx);
|
|
||||||
proto::OnTypeFormattingResponse {
|
proto::OnTypeFormattingResponse {
|
||||||
transaction: Some(transaction),
|
transaction: response
|
||||||
|
.map(|transaction| language::proto::serialize_transaction(&transaction)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
async fn response_from_proto(
|
async fn response_from_proto(
|
||||||
self,
|
self,
|
||||||
message: proto::OnTypeFormattingResponse,
|
message: proto::OnTypeFormattingResponse,
|
||||||
project: ModelHandle<Project>,
|
_: ModelHandle<Project>,
|
||||||
_: ModelHandle<Buffer>,
|
_: ModelHandle<Buffer>,
|
||||||
mut cx: AsyncAppContext,
|
_: AsyncAppContext,
|
||||||
) -> Result<ProjectTransaction> {
|
) -> Result<Option<Transaction>> {
|
||||||
let message = message
|
let Some(transaction) = message.transaction else { return Ok(None) };
|
||||||
.transaction
|
Ok(Some(language::proto::deserialize_transaction(transaction)?))
|
||||||
.ok_or_else(|| anyhow!("missing transaction"))?;
|
|
||||||
project
|
|
||||||
.update(&mut cx, |project, cx| {
|
|
||||||
project.deserialize_project_transaction(message, self.push_to_history, cx)
|
|
||||||
})
|
|
||||||
.await
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn buffer_id_from_proto(message: &proto::OnTypeFormatting) -> u64 {
|
fn buffer_id_from_proto(message: &proto::OnTypeFormatting) -> u64 {
|
||||||
|
|
|
@ -4040,9 +4040,8 @@ impl Project {
|
||||||
buffer: ModelHandle<Buffer>,
|
buffer: ModelHandle<Buffer>,
|
||||||
position: Anchor,
|
position: Anchor,
|
||||||
trigger: String,
|
trigger: String,
|
||||||
push_to_history: bool,
|
|
||||||
cx: &mut ModelContext<Self>,
|
cx: &mut ModelContext<Self>,
|
||||||
) -> Task<Result<ProjectTransaction>> {
|
) -> Task<Result<Option<Transaction>>> {
|
||||||
if self.is_local() {
|
if self.is_local() {
|
||||||
cx.spawn(|this, mut cx| async move {
|
cx.spawn(|this, mut cx| async move {
|
||||||
// Do not allow multiple concurrent formatting requests for the
|
// Do not allow multiple concurrent formatting requests for the
|
||||||
|
@ -4071,7 +4070,7 @@ impl Project {
|
||||||
.await?;
|
.await?;
|
||||||
this.update(&mut cx, |this, cx| {
|
this.update(&mut cx, |this, cx| {
|
||||||
let position = position.to_point_utf16(buffer.read(cx));
|
let position = position.to_point_utf16(buffer.read(cx));
|
||||||
this.on_type_format(buffer, position, trigger, cx)
|
this.on_type_format(buffer, position, trigger, false, cx)
|
||||||
})
|
})
|
||||||
.await
|
.await
|
||||||
})
|
})
|
||||||
|
@ -4084,16 +4083,13 @@ impl Project {
|
||||||
trigger,
|
trigger,
|
||||||
version: serialize_version(&buffer.read(cx).version()),
|
version: serialize_version(&buffer.read(cx).version()),
|
||||||
};
|
};
|
||||||
cx.spawn(|this, mut cx| async move {
|
cx.spawn(|_, _| async move {
|
||||||
let response = client
|
client
|
||||||
.request(request)
|
.request(request)
|
||||||
.await?
|
.await?
|
||||||
.transaction
|
.transaction
|
||||||
.ok_or_else(|| anyhow!("missing transaction"))?;
|
.map(language::proto::deserialize_transaction)
|
||||||
this.update(&mut cx, |this, cx| {
|
.transpose()
|
||||||
this.deserialize_project_transaction(response, push_to_history, cx)
|
|
||||||
})
|
|
||||||
.await
|
|
||||||
})
|
})
|
||||||
} else {
|
} else {
|
||||||
Task::ready(Err(anyhow!("project does not have a remote id")))
|
Task::ready(Err(anyhow!("project does not have a remote id")))
|
||||||
|
@ -4108,7 +4104,7 @@ impl Project {
|
||||||
_: Arc<CachedLspAdapter>,
|
_: Arc<CachedLspAdapter>,
|
||||||
language_server: Arc<LanguageServer>,
|
language_server: Arc<LanguageServer>,
|
||||||
cx: &mut AsyncAppContext,
|
cx: &mut AsyncAppContext,
|
||||||
) -> Result<ProjectTransaction> {
|
) -> Result<Option<Transaction>> {
|
||||||
let edits = this
|
let edits = this
|
||||||
.update(cx, |this, cx| {
|
.update(cx, |this, cx| {
|
||||||
this.edits_from_lsp(
|
this.edits_from_lsp(
|
||||||
|
@ -4139,12 +4135,7 @@ impl Project {
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
let mut project_transaction = ProjectTransaction::default();
|
Ok(transaction)
|
||||||
if let Some(transaction) = transaction {
|
|
||||||
project_transaction.0.insert(buffer_to_edit, transaction);
|
|
||||||
}
|
|
||||||
|
|
||||||
Ok(project_transaction)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
async fn deserialize_workspace_edit(
|
async fn deserialize_workspace_edit(
|
||||||
|
@ -4317,8 +4308,9 @@ impl Project {
|
||||||
buffer: ModelHandle<Buffer>,
|
buffer: ModelHandle<Buffer>,
|
||||||
position: T,
|
position: T,
|
||||||
trigger: String,
|
trigger: String,
|
||||||
|
push_to_history: bool,
|
||||||
cx: &mut ModelContext<Self>,
|
cx: &mut ModelContext<Self>,
|
||||||
) -> Task<Result<ProjectTransaction>> {
|
) -> Task<Result<Option<Transaction>>> {
|
||||||
let tab_size = buffer.read_with(cx, |buffer, cx| {
|
let tab_size = buffer.read_with(cx, |buffer, cx| {
|
||||||
let language_name = buffer.language().map(|language| language.name());
|
let language_name = buffer.language().map(|language| language.name());
|
||||||
language_settings(language_name.as_deref(), cx).tab_size
|
language_settings(language_name.as_deref(), cx).tab_size
|
||||||
|
@ -4330,7 +4322,7 @@ impl Project {
|
||||||
position,
|
position,
|
||||||
trigger,
|
trigger,
|
||||||
options: lsp_command::lsp_formatting_options(tab_size.get()).into(),
|
options: lsp_command::lsp_formatting_options(tab_size.get()).into(),
|
||||||
push_to_history: true,
|
push_to_history,
|
||||||
},
|
},
|
||||||
cx,
|
cx,
|
||||||
)
|
)
|
||||||
|
@ -5912,7 +5904,6 @@ impl Project {
|
||||||
_: Arc<Client>,
|
_: Arc<Client>,
|
||||||
mut cx: AsyncAppContext,
|
mut cx: AsyncAppContext,
|
||||||
) -> Result<proto::OnTypeFormattingResponse> {
|
) -> Result<proto::OnTypeFormattingResponse> {
|
||||||
let sender_id = envelope.original_sender_id()?;
|
|
||||||
let on_type_formatting = this.update(&mut cx, |this, cx| {
|
let on_type_formatting = this.update(&mut cx, |this, cx| {
|
||||||
let buffer = this
|
let buffer = this
|
||||||
.opened_buffers
|
.opened_buffers
|
||||||
|
@ -5928,18 +5919,15 @@ impl Project {
|
||||||
buffer,
|
buffer,
|
||||||
position,
|
position,
|
||||||
envelope.payload.trigger.clone(),
|
envelope.payload.trigger.clone(),
|
||||||
false,
|
|
||||||
cx,
|
cx,
|
||||||
))
|
))
|
||||||
})?;
|
})?;
|
||||||
|
|
||||||
let project_transaction = on_type_formatting.await?;
|
let transaction = on_type_formatting
|
||||||
let project_transaction = this.update(&mut cx, |this, cx| {
|
.await?
|
||||||
this.serialize_project_transaction_for_peer(project_transaction, sender_id, cx)
|
.as_ref()
|
||||||
});
|
.map(language::proto::serialize_transaction);
|
||||||
Ok(proto::OnTypeFormattingResponse {
|
Ok(proto::OnTypeFormattingResponse { transaction })
|
||||||
transaction: Some(project_transaction),
|
|
||||||
})
|
|
||||||
}
|
}
|
||||||
|
|
||||||
async fn handle_lsp_command<T: LspCommand>(
|
async fn handle_lsp_command<T: LspCommand>(
|
||||||
|
|
|
@ -682,7 +682,7 @@ message OnTypeFormatting {
|
||||||
}
|
}
|
||||||
|
|
||||||
message OnTypeFormattingResponse {
|
message OnTypeFormattingResponse {
|
||||||
ProjectTransaction transaction = 1;
|
Transaction transaction = 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
message PerformRenameResponse {
|
message PerformRenameResponse {
|
||||||
|
|
|
@ -6,4 +6,4 @@ pub use conn::Connection;
|
||||||
pub use peer::*;
|
pub use peer::*;
|
||||||
mod macros;
|
mod macros;
|
||||||
|
|
||||||
pub const PROTOCOL_VERSION: u32 = 55;
|
pub const PROTOCOL_VERSION: u32 = 56;
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue