1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135
//! Core primitives for building asynchronous stuff //! //! # This is [**Proposal A**](https://github.com/icorderi/rust-await/tree/proposal/a) //! //! This prposal is based on the idea of adding a single `Await` trait to the core. //! The `Await` trait would provide a common abstraction over things that we could **resume** from. //! //! In the following example (with compiler support): //! //! ```ignore //! pub **async** fn my_code() { //! // code block A //! let x = **await** some_func() //! // code block B //! } //! ``` //! //! the expectation is that _"code block B"_ will be _resumed_ whenever the `await`'ing of `some_func` returns. //! //! For now, without compiler support, it would look like: //! //! ```ignore //! pub fn my_code() { //! // code block A //! let x = some_func().await() //! // code block B //! } //! ``` pub mod examples; pub mod io; mod sync; mod thread; mod net; mod fs; pub use sync::*; pub use thread::*; pub use net::*; pub use fs::*; /// Represents then notion of something that we **could** have to _await_ for. /// /// The keyword **await** _could_ be added to the language. pub trait Await<T> { /// It will return a value when it's ready fn await(self) -> T; } /// `AwaitBox` is a version of the `Await` intended for use with _boxed_ /// objects. /// /// The idea is that where one would normally store a /// `Box<Await<T>>` in a data structure, you should use /// `Box<AwaitBox<T>>`. The two traits behave essentially the same, except /// that a `AwaitBox` can **only** be called if it is _boxed_. /// /// > Note that `AwaitBox` may be deprecated in the future if `Box<Await<T>>` /// become directly usable. pub trait AwaitBox<T> { fn await_box(self: Box<Self>) -> T; } impl<T, A> AwaitBox<T> for A where A: Await<T> { fn await_box(self: Box<Self>) -> T { self.await() } } impl<'a, T> Await<T> for Box<AwaitBox<T> + 'a> { fn await(self) -> T { self.await_box() } } impl<'a, T> Await<T> for Box<AwaitBox<T> + Send + 'a> { fn await(self) -> T { self.await_box() } } /// When they need an `Await<T>` and there is no need to wait pub struct AwaitValue<T>(pub T); impl<T> Await<T> for AwaitValue<T> { fn await(self) -> T { self.0 } } // ============================================================================ // `Await` for std types // ============================================================================ // // `Await` on `Fn` // impl<T, F: Fn() -> T> Await<T> for F { // fn await(self) -> T { // self() // } // } // `Await` on `FnOnce` impl<T, F: FnOnce() -> T> Await<T> for F { fn await(self) -> T { self() } } #[cfg(test)] mod tests { use std::thread; use Await; #[test] fn await_fn() { let x = || 8; assert_eq!(8, x.await()); } #[test] fn await_thread() { let t = thread::spawn(|| 8); assert_eq!(8, t.await().unwrap()); } #[test] fn await_box() { let x = Box::new(|| 8); assert_eq!(8, x.await()); } }