1use std::{future::Future, pin::Pin};
3
4use futures::executor::ThreadPool;
5
6pub trait Executor {
14 #[track_caller]
16 fn exec(&self, future: Pin<Box<dyn Future<Output = ()> + Send>>);
17}
18
19impl<F: Fn(Pin<Box<dyn Future<Output = ()> + Send>>)> Executor for F {
20 fn exec(&self, f: Pin<Box<dyn Future<Output = ()> + Send>>) {
21 self(f)
22 }
23}
24
25impl Executor for ThreadPool {
26 fn exec(&self, future: Pin<Box<dyn Future<Output = ()> + Send>>) {
27 self.spawn_ok(future)
28 }
29}
30
31#[cfg(all(
32 feature = "tokio",
33 not(any(target_os = "emscripten", target_os = "wasi", target_os = "unknown"))
34))]
35#[derive(Default, Debug, Clone, Copy)]
36pub(crate) struct TokioExecutor;
37#[cfg(all(
38 feature = "tokio",
39 not(any(target_os = "emscripten", target_os = "wasi", target_os = "unknown"))
40))]
41impl Executor for TokioExecutor {
42 fn exec(&self, future: Pin<Box<dyn Future<Output = ()> + Send>>) {
43 tokio::spawn(future);
44 }
45}
46
47#[cfg(all(
48 feature = "async-std",
49 not(any(target_os = "emscripten", target_os = "wasi", target_os = "unknown"))
50))]
51#[derive(Default, Debug, Clone, Copy)]
52pub(crate) struct AsyncStdExecutor;
53#[cfg(all(
54 feature = "async-std",
55 not(any(target_os = "emscripten", target_os = "wasi", target_os = "unknown"))
56))]
57impl Executor for AsyncStdExecutor {
58 fn exec(&self, future: Pin<Box<dyn Future<Output = ()> + Send>>) {
59 async_std::task::spawn(future);
60 }
61}
62
63#[cfg(feature = "wasm-bindgen")]
64#[derive(Default, Debug, Clone, Copy, Hash, PartialEq, Eq, PartialOrd, Ord)]
65pub(crate) struct WasmBindgenExecutor;
66#[cfg(feature = "wasm-bindgen")]
67impl Executor for WasmBindgenExecutor {
68 fn exec(&self, future: Pin<Box<dyn Future<Output = ()> + Send>>) {
69 wasm_bindgen_futures::spawn_local(future)
70 }
71}