2454 lines · 82.1 KB · Rust
RawDownload
use call::ActiveCall;use dap::DebugRequestType;use dap::requests::{Initialize, Launch, StackTrace};use dap::{SourceBreakpoint, requests::SetBreakpoints};use debugger_ui::debugger_panel::DebugPanel;use debugger_ui::session::DebugSession;use editor::Editor;use gpui::{Entity, TestAppContext, VisualTestContext};use project::{Project, ProjectPath, WorktreeId};use serde_json::json;use std::sync::Arc;use std::{    path::Path,    sync::atomic::{AtomicBool, Ordering},};use workspace::{Workspace, dock::Panel}; use super::{TestClient, TestServer}; pub fn init_test(cx: &mut gpui::TestAppContext) {    if std::env::var("RUST_LOG").is_ok() {        env_logger::try_init().ok();    }     cx.update(|cx| {        theme::init(theme::LoadThemes::JustBase, cx);        command_palette_hooks::init(cx);        language::init(cx);        workspace::init_settings(cx);        project::Project::init_settings(cx);        debugger_ui::init(cx);        editor::init(cx);    });} async fn add_debugger_panel(workspace: &Entity<Workspace>, cx: &mut VisualTestContext) {    let debugger_panel = workspace        .update_in(cx, |_workspace, window, cx| {            cx.spawn_in(window, DebugPanel::load)        })        .await        .unwrap();     workspace.update_in(cx, |workspace, window, cx| {        workspace.add_panel(debugger_panel, window, cx);    });} pub fn _active_session(    workspace: Entity<Workspace>,    cx: &mut VisualTestContext,) -> Entity<DebugSession> {    workspace.update_in(cx, |workspace, _window, cx| {        let debug_panel = workspace.panel::<DebugPanel>(cx).unwrap();        debug_panel            .update(cx, |this, cx| this.active_session(cx))            .unwrap()    })} struct ZedInstance<'a> {    client: TestClient,    project: Option<Entity<Project>>,    active_call: Entity<ActiveCall>,    cx: &'a mut TestAppContext,} impl<'a> ZedInstance<'a> {    fn new(client: TestClient, cx: &'a mut TestAppContext) -> Self {        ZedInstance {            project: None,            client,            active_call: cx.read(ActiveCall::global),            cx,        }    }     async fn host_project(        &mut self,        project_files: Option<serde_json::Value>,    ) -> (u64, WorktreeId) {        let (project, worktree_id) = self.client.build_local_project("/project", self.cx).await;        self.active_call            .update(self.cx, |call, cx| call.set_location(Some(&project), cx))            .await            .unwrap();         if let Some(tree) = project_files {            self.client.fs().insert_tree("/project", tree).await;        }         self.project = Some(project.clone());         let project_id = self            .active_call            .update(self.cx, |call, cx| call.share_project(project, cx))            .await            .unwrap();         (project_id, worktree_id)    }     async fn join_project(&mut self, project_id: u64) {        let remote_project = self.client.join_remote_project(project_id, self.cx).await;        self.project = Some(remote_project);         self.active_call            .update(self.cx, |call, cx| {                call.set_location(self.project.as_ref(), cx)            })            .await            .unwrap();    }     async fn expand(        &'a mut self,    ) -> (        &'a TestClient,        Entity<Workspace>,        Entity<Project>,        &'a mut VisualTestContext,    ) {        let (workspace, cx) = self.client.build_workspace(            self.project                .as_ref()                .expect("Project should be hosted or built before expanding"),            self.cx,        );        add_debugger_panel(&workspace, cx).await;        (&self.client, workspace, self.project.clone().unwrap(), cx)    }} async fn _setup_three_member_test<'a, 'b, 'c>(    server: &mut TestServer,    host_cx: &'a mut TestAppContext,    first_remote_cx: &'b mut TestAppContext,    second_remote_cx: &'c mut TestAppContext,) -> (ZedInstance<'a>, ZedInstance<'b>, ZedInstance<'c>) {    let host_client = server.create_client(host_cx, "user_host").await;    let first_remote_client = server.create_client(first_remote_cx, "user_remote_1").await;    let second_remote_client = server        .create_client(second_remote_cx, "user_remote_2")        .await;     init_test(host_cx);    init_test(first_remote_cx);    init_test(second_remote_cx);     server        .create_room(&mut [            (&host_client, host_cx),            (&first_remote_client, first_remote_cx),            (&second_remote_client, second_remote_cx),        ])        .await;     let host_zed = ZedInstance::new(host_client, host_cx);    let first_remote_zed = ZedInstance::new(first_remote_client, first_remote_cx);    let second_remote_zed = ZedInstance::new(second_remote_client, second_remote_cx);     (host_zed, first_remote_zed, second_remote_zed)} async fn setup_two_member_test<'a, 'b>(    server: &mut TestServer,    host_cx: &'a mut TestAppContext,    remote_cx: &'b mut TestAppContext,) -> (ZedInstance<'a>, ZedInstance<'b>) {    let host_client = server.create_client(host_cx, "user_host").await;    let remote_client = server.create_client(remote_cx, "user_remote").await;     init_test(host_cx);    init_test(remote_cx);     server        .create_room(&mut [(&host_client, host_cx), (&remote_client, remote_cx)])        .await;     let host_zed = ZedInstance::new(host_client, host_cx);    let remote_zed = ZedInstance::new(remote_client, remote_cx);     (host_zed, remote_zed)} #[gpui::test]async fn test_debug_panel_item_opens_on_remote(    host_cx: &mut TestAppContext,    remote_cx: &mut TestAppContext,) {    let executor = host_cx.executor();    let mut server = TestServer::start(executor).await;     let (mut host_zed, mut remote_zed) =        setup_two_member_test(&mut server, host_cx, remote_cx).await;     let (host_project_id, _) = host_zed.host_project(None).await;    remote_zed.join_project(host_project_id).await;     let (_client_host, _host_workspace, host_project, host_cx) = host_zed.expand().await;    let (_client_remote, remote_workspace, _remote_project, remote_cx) = remote_zed.expand().await;     remote_cx.run_until_parked();     let task = host_project.update(host_cx, |project, cx| {        project.start_debug_session(dap::test_config(DebugRequestType::Launch, None, None), cx)    });     let session = task.await.unwrap();    let client = session.read_with(host_cx, |project, _| project.adapter_client().unwrap());     client        .on_request::<Initialize, _>(move |_, _| {            Ok(dap::Capabilities {                supports_step_back: Some(false),                ..Default::default()            })        })        .await;     client.on_request::<Launch, _>(move |_, _| Ok(())).await;     client        .on_request::<StackTrace, _>(move |_, _| {            Ok(dap::StackTraceResponse {                stack_frames: Vec::default(),                total_frames: None,            })        })        .await;     client        .fake_event(dap::messages::Events::Stopped(dap::StoppedEvent {            reason: dap::StoppedEventReason::Pause,            description: None,            thread_id: Some(1),            preserve_focus_hint: None,            text: None,            all_threads_stopped: None,            hit_breakpoint_ids: None,        }))        .await;     host_cx.run_until_parked();    remote_cx.run_until_parked();     remote_workspace.update(remote_cx, |workspace, cx| {        let debug_panel = workspace.panel::<DebugPanel>(cx).unwrap();        let _active_session = debug_panel            .update(cx, |this, cx| this.active_session(cx))            .unwrap();         assert_eq!(            1,            debug_panel.update(cx, |this, cx| this.pane().unwrap().read(cx).items_len())        );        // assert_eq!(client.id(), active_session.read(cx).());        // assert_eq!(1, active_session.read(cx).thread_id().0);        // todo(debugger) check selected thread id    });     let shutdown_client = host_project.update(host_cx, |project, cx| {        project.dap_store().update(cx, |dap_store, cx| {            dap_store.shutdown_session(session.read(cx).session_id(), cx)        })    });     shutdown_client.await.unwrap();} #[gpui::test]async fn test_active_debug_panel_item_set_on_join_project(    host_cx: &mut TestAppContext,    remote_cx: &mut TestAppContext,) {    let executor = host_cx.executor();    let mut server = TestServer::start(executor).await;     let (mut host_zed, mut remote_zed) =        setup_two_member_test(&mut server, host_cx, remote_cx).await;     let (host_project_id, _) = host_zed.host_project(None).await;     let (_client_host, _host_workspace, host_project, host_cx) = host_zed.expand().await;     host_cx.run_until_parked();     let task = host_project.update(host_cx, |project, cx| {        project.start_debug_session(dap::test_config(DebugRequestType::Launch, None, None), cx)    });     let session = task.await.unwrap();    let client = session.read_with(host_cx, |project, _| project.adapter_client().unwrap());     client        .on_request::<Initialize, _>(move |_, _| {            Ok(dap::Capabilities {                supports_step_back: Some(false),                ..Default::default()            })        })        .await;     client.on_request::<Launch, _>(move |_, _| Ok(())).await;     client        .on_request::<StackTrace, _>(move |_, _| {            Ok(dap::StackTraceResponse {                stack_frames: Vec::default(),                total_frames: None,            })        })        .await;     client        .fake_event(dap::messages::Events::Stopped(dap::StoppedEvent {            reason: dap::StoppedEventReason::Pause,            description: None,            thread_id: Some(1),            preserve_focus_hint: None,            text: None,            all_threads_stopped: None,            hit_breakpoint_ids: None,        }))        .await;     // Give host_client time to send a debug panel item to collab server    host_cx.run_until_parked();     remote_zed.join_project(host_project_id).await;    let (_client_remote, remote_workspace, _remote_project, remote_cx) = remote_zed.expand().await;     host_cx.run_until_parked();    remote_cx.run_until_parked();     remote_workspace.update(remote_cx, |workspace, cx| {        let debug_panel = workspace.panel::<DebugPanel>(cx).unwrap();        let _active_session = debug_panel            .update(cx, |this, cx| this.active_session(cx))            .unwrap();         assert_eq!(            1,            debug_panel.update(cx, |this, cx| this.pane().unwrap().read(cx).items_len())        );        // assert_eq!(cl, active_session.read(cx).client_id());        // assert_eq!(1, active_session.read(cx).thread_id().0);        // todo(debugger)    });     let shutdown_client = host_project.update(host_cx, |project, cx| {        project.dap_store().update(cx, |dap_store, cx| {            dap_store.shutdown_session(session.read(cx).session_id(), cx)        })    });     shutdown_client.await.unwrap();     remote_cx.run_until_parked();     // assert we don't have a debug panel item anymore because the client shutdown    remote_workspace.update(remote_cx, |workspace, cx| {        let debug_panel = workspace.panel::<DebugPanel>(cx).unwrap();         debug_panel.update(cx, |this, cx| {            assert!(this.active_session(cx).is_none());            assert_eq!(0, this.pane().unwrap().read(cx).items_len());        });    });} #[gpui::test]async fn test_debug_panel_remote_button_presses(    _host_cx: &mut TestAppContext,    _remote_cx: &mut TestAppContext,) {    unimplemented!("Collab is still being refactored");    // let executor = host_cx.executor();    // let mut server = TestServer::start(executor).await;     // let (mut host_zed, mut remote_zed) =    //     setup_two_member_test(&mut server, host_cx, remote_cx).await;     // let (host_project_id, _) = host_zed.host_project(None).await;    // remote_zed.join_project(host_project_id).await;     // let (_client_host, host_workspace, host_project, host_cx) = host_zed.expand().await;    // let (_client_remote, remote_workspace, _remote_project, remote_cx) = remote_zed.expand().await;     // let task = host_project.update(host_cx, |project, cx| {    //     project.start_debug_session(dap::test_config(None), cx)    // });     // let session = task.await.unwrap();    // let client = session.read_with(host_cx, |project, _| project.adapter_client().unwrap());     // client    //     .on_request::<Initialize, _>(move |_, _| {    //         Ok(dap::Capabilities {    //             supports_step_back: Some(true),    //             ..Default::default()    //         })    //     })    //     .await;     // client.on_request::<Launch, _>(move |_, _| Ok(())).await;     // client    //     .on_request::<StackTrace, _>(move |_, _| {    //         Ok(dap::StackTraceResponse {    //             stack_frames: Vec::default(),    //             total_frames: None,    //         })    //     })    //     .await;     // client    //     .fake_event(dap::messages::Events::Stopped(dap::StoppedEvent {    //         reason: dap::StoppedEventReason::Pause,    //         description: None,    //         thread_id: Some(1),    //         preserve_focus_hint: None,    //         text: None,    //         all_threads_stopped: None,    //         hit_breakpoint_ids: None,    //     }))    //     .await;     // client    //     .on_request::<dap::requests::Continue, _>(move |_, _| {    //         Ok(dap::ContinueResponse {    //             all_threads_continued: Some(true),    //         })    //     })    //     .await;     // host_cx.run_until_parked();    // remote_cx.run_until_parked();     // let remote_debug_item = remote_workspace.update(remote_cx, |workspace, cx| {    //     let debug_panel = workspace.panel::<DebugPanel>(cx).unwrap();    //     let active_session = debug_panel    //         .update(cx, |this, cx| this.active_session(cx))    //         .unwrap();     //     assert_eq!(    //         1,    //         debug_panel.update(cx, |this, cx| this.pane().unwrap().read(cx).items_len())    //     );    //     // assert_eq!(client.id(), active_session.read(cx).client_id());    //     // assert_eq!(1, active_session.read(cx).thread_id().0);    //     // todo(debugger)    //     active_session    // });     // let local_debug_item = host_workspace.update(host_cx, |workspace, cx| {    //     let debug_panel = workspace.panel::<DebugPanel>(cx).unwrap();    //     let active_session = debug_panel    //         .update(cx, |this, cx| this.active_session(cx))    //         .unwrap();     //     assert_eq!(    //         1,    //         debug_panel.update(cx, |this, cx| this.pane().unwrap().read(cx).items_len())    //     );    //     // assert_eq!(client.id(), active_session.read(cx).client_id());    //     // assert_eq!(1, active_session.read(cx).thread_id().0);    //     // todo(debugger)    //     active_session    // });     // remote_debug_item.update(remote_cx, |this, cx| {    //     this.continue_thread(cx);    // });     // host_cx.run_until_parked();    // remote_cx.run_until_parked();     // local_debug_item.update(host_cx, |debug_panel_item, cx| {    //     assert_eq!(    //         debugger_ui::debugger_panel::ThreadStatus::Running,    //         debug_panel_item.thread_state().read(cx).status,    //     );    // });     // remote_debug_item.update(remote_cx, |debug_panel_item, cx| {    //     assert_eq!(    //         debugger_ui::debugger_panel::ThreadStatus::Running,    //         debug_panel_item.thread_state().read(cx).status,    //     );    // });     // client    //     .fake_event(dap::messages::Events::Stopped(dap::StoppedEvent {    //         reason: dap::StoppedEventReason::Pause,    //         description: None,    //         thread_id: Some(1),    //         preserve_focus_hint: None,    //         text: None,    //         all_threads_stopped: None,

Lines 1–500 of 2454.