Skip to content

Commit d336005

Browse files
ssh remoting: Fix cmd-o (#18308)
Release Notes: - ssh-remoting: Cmd-O now correctly opens files on the remote host --------- Co-authored-by: Mikayla <mikayla@zed.dev>
1 parent fdb03d3 commit d336005

File tree

15 files changed

+84
-91
lines changed

15 files changed

+84
-91
lines changed

crates/assistant/src/context_store.rs

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -357,9 +357,6 @@ impl ContextStore {
357357
let Some(project_id) = project.remote_id() else {
358358
return Task::ready(Err(anyhow!("project was not remote")));
359359
};
360-
if project.is_local_or_ssh() {
361-
return Task::ready(Err(anyhow!("cannot create remote contexts as the host")));
362-
}
363360

364361
let replica_id = project.replica_id();
365362
let capability = project.capability();
@@ -488,9 +485,6 @@ impl ContextStore {
488485
let Some(project_id) = project.remote_id() else {
489486
return Task::ready(Err(anyhow!("project was not remote")));
490487
};
491-
if project.is_local_or_ssh() {
492-
return Task::ready(Err(anyhow!("cannot open remote contexts as the host")));
493-
}
494488

495489
if let Some(context) = self.loaded_context_for_id(&context_id, cx) {
496490
return Task::ready(Ok(context));

crates/collab/src/tests/random_project_collaboration_tests.rs

Lines changed: 4 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -298,8 +298,7 @@ impl RandomizedTest for ProjectCollaborationTest {
298298
continue;
299299
};
300300
let project_root_name = root_name_for_project(&project, cx);
301-
let is_local =
302-
project.read_with(cx, |project, _| project.is_local_or_ssh());
301+
let is_local = project.read_with(cx, |project, _| project.is_local());
303302
let worktree = project.read_with(cx, |project, cx| {
304303
project
305304
.worktrees(cx)
@@ -335,7 +334,7 @@ impl RandomizedTest for ProjectCollaborationTest {
335334
continue;
336335
};
337336
let project_root_name = root_name_for_project(&project, cx);
338-
let is_local = project.read_with(cx, |project, _| project.is_local_or_ssh());
337+
let is_local = project.read_with(cx, |project, _| project.is_local());
339338

340339
match rng.gen_range(0..100_u32) {
341340
// Manipulate an existing buffer
@@ -1256,7 +1255,7 @@ impl RandomizedTest for ProjectCollaborationTest {
12561255
let buffers = client.buffers().clone();
12571256
for (guest_project, guest_buffers) in &buffers {
12581257
let project_id = if guest_project.read_with(client_cx, |project, _| {
1259-
project.is_local_or_ssh() || project.is_disconnected()
1258+
project.is_local() || project.is_disconnected()
12601259
}) {
12611260
continue;
12621261
} else {
@@ -1560,9 +1559,7 @@ async fn ensure_project_shared(
15601559
let first_root_name = root_name_for_project(project, cx);
15611560
let active_call = cx.read(ActiveCall::global);
15621561
if active_call.read_with(cx, |call, _| call.room().is_some())
1563-
&& project.read_with(cx, |project, _| {
1564-
project.is_local_or_ssh() && !project.is_shared()
1565-
})
1562+
&& project.read_with(cx, |project, _| project.is_local() && !project.is_shared())
15661563
{
15671564
match active_call
15681565
.update(cx, |call, cx| call.share_project(project.clone(), cx))

crates/editor/src/editor.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11819,7 +11819,7 @@ impl Editor {
1181911819
.filter_map(|buffer| {
1182011820
let buffer = buffer.read(cx);
1182111821
let language = buffer.language()?;
11822-
if project.is_local_or_ssh()
11822+
if project.is_local()
1182311823
&& project.language_servers_for_buffer(buffer, cx).count() == 0
1182411824
{
1182511825
None

crates/feedback/src/feedback_modal.rs

Lines changed: 29 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,7 @@ use regex::Regex;
1818
use serde_derive::Serialize;
1919
use ui::{prelude::*, Button, ButtonStyle, IconPosition, Tooltip};
2020
use util::ResultExt;
21-
use workspace::notifications::NotificationId;
22-
use workspace::{DismissDecision, ModalView, Toast, Workspace};
21+
use workspace::{DismissDecision, ModalView, Workspace};
2322

2423
use crate::{system_specs::SystemSpecs, GiveFeedback, OpenZedRepo};
2524

@@ -120,44 +119,34 @@ impl FeedbackModal {
120119
pub fn register(workspace: &mut Workspace, cx: &mut ViewContext<Workspace>) {
121120
let _handle = cx.view().downgrade();
122121
workspace.register_action(move |workspace, _: &GiveFeedback, cx| {
123-
let markdown = workspace
124-
.app_state()
125-
.languages
126-
.language_for_name("Markdown");
127-
128-
let project = workspace.project().clone();
129-
let is_local_project = project.read(cx).is_local_or_ssh();
130-
131-
if !is_local_project {
132-
struct FeedbackInRemoteProject;
133-
134-
workspace.show_toast(
135-
Toast::new(
136-
NotificationId::unique::<FeedbackInRemoteProject>(),
137-
"You can only submit feedback in your own project.",
138-
),
139-
cx,
140-
);
141-
return;
142-
}
143-
144-
let system_specs = SystemSpecs::new(cx);
145-
cx.spawn(|workspace, mut cx| async move {
146-
let markdown = markdown.await.log_err();
147-
let buffer = project.update(&mut cx, |project, cx| {
148-
project.create_local_buffer("", markdown, cx)
149-
})?;
150-
let system_specs = system_specs.await;
151-
152-
workspace.update(&mut cx, |workspace, cx| {
153-
workspace.toggle_modal(cx, move |cx| {
154-
FeedbackModal::new(system_specs, project, buffer, cx)
155-
});
156-
})?;
157-
158-
anyhow::Ok(())
159-
})
160-
.detach_and_log_err(cx);
122+
workspace
123+
.with_local_workspace(cx, |workspace, cx| {
124+
let markdown = workspace
125+
.app_state()
126+
.languages
127+
.language_for_name("Markdown");
128+
129+
let project = workspace.project().clone();
130+
131+
let system_specs = SystemSpecs::new(cx);
132+
cx.spawn(|workspace, mut cx| async move {
133+
let markdown = markdown.await.log_err();
134+
let buffer = project.update(&mut cx, |project, cx| {
135+
project.create_local_buffer("", markdown, cx)
136+
})?;
137+
let system_specs = system_specs.await;
138+
139+
workspace.update(&mut cx, |workspace, cx| {
140+
workspace.toggle_modal(cx, move |cx| {
141+
FeedbackModal::new(system_specs, project, buffer, cx)
142+
});
143+
})?;
144+
145+
anyhow::Ok(())
146+
})
147+
.detach_and_log_err(cx);
148+
})
149+
.detach_and_log_err(cx);
161150
});
162151
}
163152

crates/file_finder/src/file_finder.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -884,7 +884,7 @@ impl PickerDelegate for FileFinderDelegate {
884884
project
885885
.worktree_for_id(history_item.project.worktree_id, cx)
886886
.is_some()
887-
|| (project.is_local_or_ssh() && history_item.absolute.is_some())
887+
|| (project.is_local() && history_item.absolute.is_some())
888888
}),
889889
self.currently_opened_path.as_ref(),
890890
None,

crates/language_tools/src/lsp_log.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -184,7 +184,7 @@ pub fn init(cx: &mut AppContext) {
184184

185185
cx.observe_new_views(move |workspace: &mut Workspace, cx| {
186186
let project = workspace.project();
187-
if project.read(cx).is_local_or_ssh() {
187+
if project.read(cx).is_local() {
188188
log_store.update(cx, |store, cx| {
189189
store.add_project(project, cx);
190190
});
@@ -193,7 +193,7 @@ pub fn init(cx: &mut AppContext) {
193193
let log_store = log_store.clone();
194194
workspace.register_action(move |workspace, _: &OpenLanguageServerLogs, cx| {
195195
let project = workspace.project().read(cx);
196-
if project.is_local_or_ssh() {
196+
if project.is_local() {
197197
workspace.add_item_to_active_pane(
198198
Box::new(cx.new_view(|cx| {
199199
LspLogView::new(workspace.project().clone(), log_store.clone(), cx)

crates/outline_panel/src/outline_panel.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3909,7 +3909,7 @@ impl Render for OutlinePanel {
39093909
.when(project.is_local(), |el| {
39103910
el.on_action(cx.listener(Self::reveal_in_finder))
39113911
})
3912-
.when(project.is_local_or_ssh(), |el| {
3912+
.when(project.is_local() || project.is_via_ssh(), |el| {
39133913
el.on_action(cx.listener(Self::open_in_terminal))
39143914
})
39153915
.on_mouse_down(

crates/project/src/project.rs

Lines changed: 26 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -487,7 +487,7 @@ impl DirectoryLister {
487487
pub fn is_local(&self, cx: &AppContext) -> bool {
488488
match self {
489489
DirectoryLister::Local(_) => true,
490-
DirectoryLister::Project(project) => project.read(cx).is_local_or_ssh(),
490+
DirectoryLister::Project(project) => project.read(cx).is_local(),
491491
}
492492
}
493493

@@ -1199,7 +1199,13 @@ impl Project {
11991199
self.dev_server_project_id
12001200
}
12011201

1202-
pub fn supports_remote_terminal(&self, cx: &AppContext) -> bool {
1202+
pub fn supports_terminal(&self, cx: &AppContext) -> bool {
1203+
if self.is_local() {
1204+
return true;
1205+
}
1206+
if self.is_via_ssh() {
1207+
return true;
1208+
}
12031209
let Some(id) = self.dev_server_project_id else {
12041210
return false;
12051211
};
@@ -1213,10 +1219,6 @@ impl Project {
12131219
}
12141220

12151221
pub fn ssh_connection_string(&self, cx: &ModelContext<Self>) -> Option<SharedString> {
1216-
if self.is_local_or_ssh() {
1217-
return None;
1218-
}
1219-
12201222
let dev_server_id = self.dev_server_project_id()?;
12211223
dev_server_projects::Store::global(cx)
12221224
.read(cx)
@@ -1643,13 +1645,6 @@ impl Project {
16431645
}
16441646
}
16451647

1646-
pub fn is_local_or_ssh(&self) -> bool {
1647-
match &self.client_state {
1648-
ProjectClientState::Local | ProjectClientState::Shared { .. } => true,
1649-
ProjectClientState::Remote { .. } => false,
1650-
}
1651-
}
1652-
16531648
pub fn is_via_ssh(&self) -> bool {
16541649
match &self.client_state {
16551650
ProjectClientState::Local | ProjectClientState::Shared { .. } => {
@@ -1735,7 +1730,7 @@ impl Project {
17351730
) -> Task<Result<Model<Buffer>>> {
17361731
if let Some(buffer) = self.buffer_for_id(id, cx) {
17371732
Task::ready(Ok(buffer))
1738-
} else if self.is_local_or_ssh() {
1733+
} else if self.is_local() || self.is_via_ssh() {
17391734
Task::ready(Err(anyhow!("buffer {} does not exist", id)))
17401735
} else if let Some(project_id) = self.remote_id() {
17411736
let request = self.client.request(proto::OpenBufferById {
@@ -1857,7 +1852,7 @@ impl Project {
18571852
let mut changes = rx.ready_chunks(MAX_BATCH_SIZE);
18581853

18591854
while let Some(changes) = changes.next().await {
1860-
let is_local = this.update(&mut cx, |this, _| this.is_local_or_ssh())?;
1855+
let is_local = this.update(&mut cx, |this, _| this.is_local())?;
18611856

18621857
for change in changes {
18631858
match change {
@@ -2001,7 +1996,7 @@ impl Project {
20011996
language_server_id,
20021997
message,
20031998
} => {
2004-
if self.is_local_or_ssh() {
1999+
if self.is_local() {
20052000
self.enqueue_buffer_ordered_message(
20062001
BufferOrderedMessage::LanguageServerUpdate {
20072002
language_server_id: *language_server_id,
@@ -3039,8 +3034,19 @@ impl Project {
30393034
query: String,
30403035
cx: &mut ModelContext<Self>,
30413036
) -> Task<Result<Vec<PathBuf>>> {
3042-
if self.is_local_or_ssh() {
3037+
if self.is_local() {
30433038
DirectoryLister::Local(self.fs.clone()).list_directory(query, cx)
3039+
} else if let Some(session) = self.ssh_session.as_ref() {
3040+
let request = proto::ListRemoteDirectory {
3041+
dev_server_id: SSH_PROJECT_ID,
3042+
path: query,
3043+
};
3044+
3045+
let response = session.request(request);
3046+
cx.background_executor().spawn(async move {
3047+
let response = response.await?;
3048+
Ok(response.entries.into_iter().map(PathBuf::from).collect())
3049+
})
30443050
} else if let Some(dev_server) = self.dev_server_project_id().and_then(|id| {
30453051
dev_server_projects::Store::global(cx)
30463052
.read(cx)
@@ -3317,7 +3323,7 @@ impl Project {
33173323
mut cx: AsyncAppContext,
33183324
) -> Result<()> {
33193325
this.update(&mut cx, |this, cx| {
3320-
if this.is_local_or_ssh() {
3326+
if this.is_local() || this.is_via_ssh() {
33213327
this.unshare(cx)?;
33223328
} else {
33233329
this.disconnected_from_host(cx);
@@ -3995,7 +4001,7 @@ impl Project {
39954001
location: Location,
39964002
cx: &mut ModelContext<'_, Project>,
39974003
) -> Task<Option<TaskContext>> {
3998-
if self.is_local_or_ssh() {
4004+
if self.is_local() {
39994005
let (worktree_id, worktree_abs_path) = if let Some(worktree) = self.task_worktree(cx) {
40004006
(
40014007
Some(worktree.read(cx).id()),
@@ -4081,7 +4087,7 @@ impl Project {
40814087
location: Option<Location>,
40824088
cx: &mut ModelContext<Self>,
40834089
) -> Task<Result<Vec<(TaskSourceKind, TaskTemplate)>>> {
4084-
if self.is_local_or_ssh() {
4090+
if self.is_local() {
40854091
let (file, language) = location
40864092
.map(|location| {
40874093
let buffer = location.buffer.read(cx);

crates/project_panel/src/project_panel.rs

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2722,11 +2722,14 @@ impl Render for ProjectPanel {
27222722
}
27232723
}))
27242724
})
2725-
.when(project.is_local_or_ssh(), |el| {
2725+
.when(project.is_local(), |el| {
27262726
el.on_action(cx.listener(Self::reveal_in_finder))
27272727
.on_action(cx.listener(Self::open_system))
27282728
.on_action(cx.listener(Self::open_in_terminal))
27292729
})
2730+
.when(project.is_via_ssh(), |el| {
2731+
el.on_action(cx.listener(Self::open_in_terminal))
2732+
})
27302733
.on_mouse_down(
27312734
MouseButton::Right,
27322735
cx.listener(move |this, event: &MouseDownEvent, cx| {

crates/tasks_ui/src/lib.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -94,7 +94,7 @@ fn toggle_modal(workspace: &mut Workspace, cx: &mut ViewContext<'_, Workspace>)
9494
workspace
9595
.update(&mut cx, |workspace, cx| {
9696
if workspace.project().update(cx, |project, cx| {
97-
project.is_local_or_ssh() || project.ssh_connection_string(cx).is_some()
97+
project.is_local() || project.ssh_connection_string(cx).is_some()
9898
}) {
9999
workspace.toggle_modal(cx, |cx| {
100100
TasksModal::new(project, task_context, workspace_handle, cx)

0 commit comments

Comments
 (0)