Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Move requests into client #112

Merged
merged 23 commits into from
Feb 13, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
23 commits
Select commit Hold shift + click to select a range
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

32 changes: 18 additions & 14 deletions crates/collab/src/tests/debug_panel_tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -269,7 +269,7 @@ async fn test_debug_panel_item_opens_on_remote(
debug_panel.update(cx, |this, cx| this.pane().unwrap().read(cx).items_len())
);
assert_eq!(client.id(), active_debug_panel_item.read(cx).client_id());
assert_eq!(1, active_debug_panel_item.read(cx).thread_id());
assert_eq!(1, active_debug_panel_item.read(cx).thread_id().0);
});

let shutdown_client = host_project.update(host_cx, |project, cx| {
Expand Down Expand Up @@ -368,7 +368,7 @@ async fn test_active_debug_panel_item_set_on_join_project(
debug_panel.update(cx, |this, cx| this.pane().unwrap().read(cx).items_len())
);
assert_eq!(client.id(), active_debug_panel_item.read(cx).client_id());
assert_eq!(1, active_debug_panel_item.read(cx).thread_id());
assert_eq!(1, active_debug_panel_item.read(cx).thread_id().0);
});

let shutdown_client = host_project.update(host_cx, |project, cx| {
Expand Down Expand Up @@ -481,7 +481,7 @@ async fn test_debug_panel_remote_button_presses(
debug_panel.update(cx, |this, cx| this.pane().unwrap().read(cx).items_len())
);
assert_eq!(client.id(), active_debug_panel_item.read(cx).client_id());
assert_eq!(1, active_debug_panel_item.read(cx).thread_id());
assert_eq!(1, active_debug_panel_item.read(cx).thread_id().0);
active_debug_panel_item
});

Expand All @@ -496,7 +496,7 @@ async fn test_debug_panel_remote_button_presses(
debug_panel.update(cx, |this, cx| this.pane().unwrap().read(cx).items_len())
);
assert_eq!(client.id(), active_debug_panel_item.read(cx).client_id());
assert_eq!(1, active_debug_panel_item.read(cx).thread_id());
assert_eq!(1, active_debug_panel_item.read(cx).thread_id().0);
active_debug_panel_item
});

Expand Down Expand Up @@ -1251,7 +1251,9 @@ async fn test_module_list(
debug_panel_item.update(cx, |item, cx| {
assert_eq!(
true,
item.capabilities(cx).supports_modules_request.unwrap(),
item.capabilities(cx)
.and_then(|caps| caps.supports_modules_request)
.unwrap(),
"Local supports modules request should be true"
);

Expand Down Expand Up @@ -1279,7 +1281,9 @@ async fn test_module_list(
debug_panel_item.update(cx, |item, cx| {
assert_eq!(
true,
item.capabilities(cx).supports_modules_request.unwrap(),
item.capabilities(cx)
.and_then(|caps| caps.supports_modules_request)
.unwrap(),
"Remote capabilities supports modules request should be true"
);
let remote_module_list = item.module_list().update(cx, |list, cx| list.modules(cx));
Expand Down Expand Up @@ -1310,7 +1314,9 @@ async fn test_module_list(
debug_panel_item.update(cx, |item, cx| {
assert_eq!(
true,
item.capabilities(cx).supports_modules_request.unwrap(),
item.capabilities(cx)
.and_then(|caps| caps.supports_modules_request)
.unwrap(),
"Remote (mid session join) capabilities supports modules request should be true"
);
let remote_module_list = item.module_list().update(cx, |list, cx| list.modules(cx));
Expand Down Expand Up @@ -1950,9 +1956,7 @@ async fn test_ignore_breakpoints(
let session_id = debug_panel.update(cx, |this, cx| {
this.dap_store()
.read(cx)
.as_remote()
.unwrap()
.session_by_client_id(&client.id())
.session_by_client_id(client.id())
.unwrap()
.read(cx)
.id()
Expand All @@ -1966,7 +1970,7 @@ async fn test_ignore_breakpoints(
);
assert_eq!(false, breakpoints_ignored);
assert_eq!(client.id(), active_debug_panel_item.read(cx).client_id());
assert_eq!(1, active_debug_panel_item.read(cx).thread_id());
assert_eq!(1, active_debug_panel_item.read(cx).thread_id().0);
active_debug_panel_item
});

Expand Down Expand Up @@ -2004,7 +2008,7 @@ async fn test_ignore_breakpoints(
active_debug_panel_item.read(cx).are_breakpoints_ignored(cx)
);
assert_eq!(client.id(), active_debug_panel_item.read(cx).client_id());
assert_eq!(1, active_debug_panel_item.read(cx).thread_id());
assert_eq!(1, active_debug_panel_item.read(cx).thread_id().0);

active_debug_panel_item
});
Expand Down Expand Up @@ -2064,7 +2068,7 @@ async fn test_ignore_breakpoints(

assert_eq!(true, breakpoints_ignored);
assert_eq!(client.id(), debug_panel.client_id());
assert_eq!(1, debug_panel.thread_id());
assert_eq!(1, debug_panel.thread_id().0);
});

client
Expand Down Expand Up @@ -2135,7 +2139,7 @@ async fn test_ignore_breakpoints(
debug_panel.update(cx, |this, cx| this.pane().unwrap().read(cx).items_len())
);
assert_eq!(client.id(), active_debug_panel_item.read(cx).client_id());
assert_eq!(1, active_debug_panel_item.read(cx).thread_id());
assert_eq!(1, active_debug_panel_item.read(cx).thread_id().0);
active_debug_panel_item
});

Expand Down
5 changes: 3 additions & 2 deletions crates/dap/src/client.rs
Original file line number Diff line number Diff line change
Expand Up @@ -27,18 +27,19 @@ const DAP_REQUEST_TIMEOUT: Duration = Duration::from_secs(12);

#[derive(Copy, Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
#[repr(transparent)]
pub struct DebugAdapterClientId(pub usize);
pub struct DebugAdapterClientId(pub u32);

impl DebugAdapterClientId {
pub fn from_proto(client_id: u64) -> Self {
Self(client_id as usize)
Self(client_id as u32)
}

pub fn to_proto(&self) -> u64 {
self.0 as u64
}
}

/// Represents a connection to the debug adapter process, either via stdout/stdin or a socket.
pub struct DebugAdapterClient {
id: DebugAdapterClientId,
sequence_count: AtomicU64,
Expand Down
152 changes: 150 additions & 2 deletions crates/dap/src/proto_conversions.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
use anyhow::{anyhow, Result};
use client::proto::{
self, DapChecksum, DapChecksumAlgorithm, DapModule, DapScope, DapScopePresentationHint,
DapSource, DapSourcePresentationHint, DapStackFrame, DapVariable, SetDebugClientCapabilities,
self, DapChecksum, DapChecksumAlgorithm, DapEvaluateContext, DapModule, DapScope,
DapScopePresentationHint, DapSource, DapSourcePresentationHint, DapStackFrame, DapVariable,
SetDebugClientCapabilities,
};
use dap_types::{
Capabilities, OutputEventCategory, OutputEventGroup, ScopePresentationHint, Source,
Expand Down Expand Up @@ -490,3 +491,150 @@ impl ProtoConversion for dap_types::OutputEventGroup {
}
}
}

impl ProtoConversion for dap_types::CompletionItem {
type ProtoType = proto::DapCompletionItem;
type Output = Self;

fn to_proto(&self) -> Self::ProtoType {
proto::DapCompletionItem {
label: self.label.clone(),
text: self.text.clone(),
detail: self.detail.clone(),
typ: self
.type_
.as_ref()
.map(ProtoConversion::to_proto)
.map(|typ| typ.into()),
start: self.start,
length: self.length,
selection_start: self.selection_start,
selection_length: self.selection_length,
sort_text: self.sort_text.clone(),
}
}

fn from_proto(payload: Self::ProtoType) -> Self {
let typ = payload.typ(); // todo(debugger): This might be a potential issue/bug because it defaults to a type when it's None

Self {
label: payload.label,
detail: payload.detail,
sort_text: payload.sort_text,
text: payload.text.clone(),
type_: Some(dap_types::CompletionItemType::from_proto(typ)),
start: payload.start,
length: payload.length,
selection_start: payload.selection_start,
selection_length: payload.selection_length,
}
}
}

impl ProtoConversion for dap_types::EvaluateArgumentsContext {
type ProtoType = DapEvaluateContext;
type Output = Self;

fn to_proto(&self) -> Self::ProtoType {
match self {
dap_types::EvaluateArgumentsContext::Variables => {
proto::DapEvaluateContext::EvaluateVariables
}
dap_types::EvaluateArgumentsContext::Watch => proto::DapEvaluateContext::Watch,
dap_types::EvaluateArgumentsContext::Hover => proto::DapEvaluateContext::Hover,
dap_types::EvaluateArgumentsContext::Repl => proto::DapEvaluateContext::Repl,
dap_types::EvaluateArgumentsContext::Clipboard => proto::DapEvaluateContext::Clipboard,
dap_types::EvaluateArgumentsContext::Unknown => {
proto::DapEvaluateContext::EvaluateUnknown
}
_ => proto::DapEvaluateContext::EvaluateUnknown,
}
}

fn from_proto(payload: Self::ProtoType) -> Self {
match payload {
proto::DapEvaluateContext::EvaluateVariables => {
dap_types::EvaluateArgumentsContext::Variables
}
proto::DapEvaluateContext::Watch => dap_types::EvaluateArgumentsContext::Watch,
proto::DapEvaluateContext::Hover => dap_types::EvaluateArgumentsContext::Hover,
proto::DapEvaluateContext::Repl => dap_types::EvaluateArgumentsContext::Repl,
proto::DapEvaluateContext::Clipboard => dap_types::EvaluateArgumentsContext::Clipboard,
proto::DapEvaluateContext::EvaluateUnknown => {
dap_types::EvaluateArgumentsContext::Unknown
}
}
}
}

impl ProtoConversion for dap_types::CompletionItemType {
type ProtoType = proto::DapCompletionItemType;
type Output = Self;

fn to_proto(&self) -> Self::ProtoType {
match self {
dap_types::CompletionItemType::Class => proto::DapCompletionItemType::Class,
dap_types::CompletionItemType::Color => proto::DapCompletionItemType::Color,
dap_types::CompletionItemType::Constructor => proto::DapCompletionItemType::Constructor,
dap_types::CompletionItemType::Customcolor => proto::DapCompletionItemType::Customcolor,
dap_types::CompletionItemType::Enum => proto::DapCompletionItemType::Enum,
dap_types::CompletionItemType::Field => proto::DapCompletionItemType::Field,
dap_types::CompletionItemType::File => proto::DapCompletionItemType::CompletionItemFile,
dap_types::CompletionItemType::Function => proto::DapCompletionItemType::Function,
dap_types::CompletionItemType::Interface => proto::DapCompletionItemType::Interface,
dap_types::CompletionItemType::Keyword => proto::DapCompletionItemType::Keyword,
dap_types::CompletionItemType::Method => proto::DapCompletionItemType::Method,
dap_types::CompletionItemType::Module => proto::DapCompletionItemType::Module,
dap_types::CompletionItemType::Property => proto::DapCompletionItemType::Property,
dap_types::CompletionItemType::Reference => proto::DapCompletionItemType::Reference,
dap_types::CompletionItemType::Snippet => proto::DapCompletionItemType::Snippet,
dap_types::CompletionItemType::Text => proto::DapCompletionItemType::Text,
dap_types::CompletionItemType::Unit => proto::DapCompletionItemType::Unit,
dap_types::CompletionItemType::Value => proto::DapCompletionItemType::Value,
dap_types::CompletionItemType::Variable => proto::DapCompletionItemType::Variable,
}
}

fn from_proto(payload: Self::ProtoType) -> Self {
match payload {
proto::DapCompletionItemType::Class => dap_types::CompletionItemType::Class,
proto::DapCompletionItemType::Color => dap_types::CompletionItemType::Color,
proto::DapCompletionItemType::CompletionItemFile => dap_types::CompletionItemType::File,
proto::DapCompletionItemType::Constructor => dap_types::CompletionItemType::Constructor,
proto::DapCompletionItemType::Customcolor => dap_types::CompletionItemType::Customcolor,
proto::DapCompletionItemType::Enum => dap_types::CompletionItemType::Enum,
proto::DapCompletionItemType::Field => dap_types::CompletionItemType::Field,
proto::DapCompletionItemType::Function => dap_types::CompletionItemType::Function,
proto::DapCompletionItemType::Interface => dap_types::CompletionItemType::Interface,
proto::DapCompletionItemType::Keyword => dap_types::CompletionItemType::Keyword,
proto::DapCompletionItemType::Method => dap_types::CompletionItemType::Method,
proto::DapCompletionItemType::Module => dap_types::CompletionItemType::Module,
proto::DapCompletionItemType::Property => dap_types::CompletionItemType::Property,
proto::DapCompletionItemType::Reference => dap_types::CompletionItemType::Reference,
proto::DapCompletionItemType::Snippet => dap_types::CompletionItemType::Snippet,
proto::DapCompletionItemType::Text => dap_types::CompletionItemType::Text,
proto::DapCompletionItemType::Unit => dap_types::CompletionItemType::Unit,
proto::DapCompletionItemType::Value => dap_types::CompletionItemType::Value,
proto::DapCompletionItemType::Variable => dap_types::CompletionItemType::Variable,
}
}
}

impl ProtoConversion for dap_types::Thread {
type ProtoType = proto::DapThread;
type Output = Self;

fn to_proto(&self) -> Self::ProtoType {
proto::DapThread {
id: self.id,
name: self.name.clone(),
}
}

fn from_proto(payload: Self::ProtoType) -> Self {
Self {
id: payload.id,
name: payload.name,
}
}
}
15 changes: 9 additions & 6 deletions crates/debugger_tools/src/dap_log.rs
Original file line number Diff line number Diff line change
Expand Up @@ -174,9 +174,13 @@ impl LogStore {
this.add_debug_client(
*client_id,
project.update(cx, |project, cx| {
project
.dap_store()
.update(cx, |store, cx| store.client_by_id(client_id, cx))
project.dap_store().update(cx, |store, cx| {
store.client_by_id(client_id, cx).and_then(
|(session, client)| {
Some((session, client.read(cx).adapter_client()?))
},
)
})
}),
);
}
Expand Down Expand Up @@ -587,9 +591,8 @@ impl DapLogView {
session_name: session.read(cx).name(),
clients: {
let mut clients = session
.read(cx)
.as_local()?
.clients()
.read_with(cx, |session, cx| session.clients(cx))
.iter()
.map(|client| DapMenuSubItem {
client_id: client.id(),
client_name: client.adapter_id(),
Expand Down
12 changes: 7 additions & 5 deletions crates/debugger_ui/src/attach_modal.rs
Original file line number Diff line number Diff line change
Expand Up @@ -53,14 +53,14 @@ pub(crate) struct AttachModal {
impl AttachModal {
pub fn new(
session_id: &DebugSessionId,
client_id: &DebugAdapterClientId,
client_id: DebugAdapterClientId,
dap_store: Entity<DapStore>,
window: &mut Window,
cx: &mut Context<Self>,
) -> Self {
let picker = cx.new(|cx| {
Picker::uniform_list(
AttachModalDelegate::new(*session_id, *client_id, dap_store),
AttachModalDelegate::new(*session_id, client_id, dap_store),
window,
cx,
)
Expand Down Expand Up @@ -130,8 +130,10 @@ impl PickerDelegate for AttachModalDelegate {
if let Some(processes) = this.delegate.candidates.clone() {
processes
} else {
let Some((_, client)) = this.delegate.dap_store.update(cx, |store, cx| {
store.client_by_id(&this.delegate.client_id, cx)
let Some(client) = this.delegate.dap_store.update(cx, |store, cx| {
store
.client_by_id(&this.delegate.client_id, cx)
.and_then(|(_, client)| client.read(cx).adapter_client())
}) else {
return Vec::new();
};
Expand Down Expand Up @@ -222,7 +224,7 @@ impl PickerDelegate for AttachModalDelegate {

self.dap_store.update(cx, |store, cx| {
store
.attach(&self.session_id, &self.client_id, candidate.pid, cx)
.attach(&self.session_id, self.client_id, candidate.pid, cx)
.detach_and_log_err(cx);
});

Expand Down
Loading