use crate::App;
use gpui_util::{TryFutureExt, TryFutureExtBacktrace};
use scheduler::Task;
pub trait TaskExt<T, E> {
fn detach_and_log_err(self, cx: &App);
fn detach_and_log_err_with_backtrace(self, cx: &App);
}
impl<T, E> TaskExt<T, E> for Task<Result<T, E>>
where
T: 'static,
E: 'static + std::fmt::Display + std::fmt::Debug,
{
#[track_caller]
fn detach_and_log_err(self, cx: &App) {
let location = core::panic::Location::caller();
cx.foreground_executor()
.spawn(self.log_tracked_err(*location))
.detach();
}
#[track_caller]
fn detach_and_log_err_with_backtrace(self, cx: &App) {
let location = *core::panic::Location::caller();
cx.foreground_executor()
.spawn(self.log_tracked_err_with_backtrace(location))
.detach();
}
}
#[cfg(test)]
mod test {
use crate::{App, BackgroundExecutor, ForegroundExecutor, TestDispatcher, TestPlatform};
use std::{cell::RefCell, rc::Rc, sync::Arc};
fn create_test_app() -> (TestDispatcher, BackgroundExecutor, Rc<crate::AppCell>) {
let dispatcher = TestDispatcher::new(0);
let arc_dispatcher = Arc::new(dispatcher.clone());
let background_executor = BackgroundExecutor::new(arc_dispatcher.clone());
let foreground_executor = ForegroundExecutor::new(arc_dispatcher);
let platform = TestPlatform::new(background_executor.clone(), foreground_executor);
let asset_source = Arc::new(());
let http_client = http_client::FakeHttpClient::with_404_response();
let app = App::new_app(platform, asset_source, http_client);
(dispatcher, background_executor, app)
}
#[test]
fn sanity_test_tasks_run() {
let (dispatcher, _background_executor, app) = create_test_app();
let foreground_executor = app.borrow().foreground_executor.clone();
let task_ran = Rc::new(RefCell::new(false));
foreground_executor
.spawn({
let task_ran = Rc::clone(&task_ran);
async move {
*task_ran.borrow_mut() = true;
}
})
.detach();
dispatcher.run_until_parked();
assert!(
*task_ran.borrow(),
"Task should run normally when app is alive"
);
}
}