https://github.com/kijewski/named-future
https://github.com/kijewski/named-future
Last synced: about 1 year ago
JSON representation
- Host: GitHub
- URL: https://github.com/kijewski/named-future
- Owner: Kijewski
- License: apache-2.0
- Created: 2023-04-22T17:55:24.000Z (about 3 years ago)
- Default Branch: main
- Last Pushed: 2024-01-08T01:02:26.000Z (over 2 years ago)
- Last Synced: 2025-01-24T17:34:40.125Z (over 1 year ago)
- Language: Rust
- Homepage: https://docs.rs/named-future
- Size: 37.1 KB
- Stars: 0
- Watchers: 1
- Forks: 0
- Open Issues: 1
-
Metadata Files:
- Readme: README.md
- License: LICENSE.md
Awesome Lists containing this project
README
# named-future: *Give your Future a name!*
[](https://github.com/Kijewski/named-future/actions/workflows/ci.yml)
[](https://crates.io/crates/named-future)

[](/LICENSE.md "License: Apache-2.0 WITH LLVM-exception")
Wrap a [`Future`] in a sized struct, so it can be use in traits, or as return type,
without the need for [`Box<…>`], [`dyn …`], or [`impl …`].
A simple workaround until [`#![feature(type_alias_impl_trait)]`][tait] is stabilized:
```rust,untested
/// A slow multiplication
///
/// # Struct
///
/// Future generated by [`slow_mul`]
#[named_future]
pub async fn slow_mul(factor1: u32, factor2: u32) -> u32 {
sleep(Duration::from_secs(5)).await;
factor1 * factor2
}
```
Expands to:
```rust,untested
/// A slow multiplication
pub fn slow_mul(factor1: u32, factor2: u32) -> SlowMul {
...
}
/// Future generated by [`slow_mul`]
pub struct SlowMul {
...
}
impl Future for SlowMul {
type Output = u32;
#[inline]
fn poll(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll {
...
}
}
```
Additionally it will implement a `Drop`, so a dropped future will work fine,
and `Debug` for your convenience.
The proc_macro `#[named_future]` has the following optional arguments:
- **`#[named_future(Send)]`**
- Implement [`Send`] for the generated `struct`.
It is currently not possible to detect automatically if the `struct` should be `Send`,
so you have to ask for the implementation manually.
Even so, it is ensured that the [`Future`] is send, and the compilation will fail otherwise.
- **`#[named_future(Sync)]`**
- Implement [`Sync`] for the generated `struct`. Please see the explanation for `Send`.
- **#\[named_future(type = Name)\]**
- Instead of the default name, i.e. using pascal case of the function name,
you can override the name using this argument.
You can also override the visibility of the `struct` using this argument: `type = pub Name`.
By default, the visibility of the function is copied.
- **#\[named_future(crate = some::path)\]**
- If you have renamed the dependency in your `Cargo.toml`,
e.g. `renamed = { package = "named-future", version = "0.0.1" }`,
then you have to specify its name / path.
Defaults to `::named_future`.
To add a documentation to your function, and the generated struct,
you can separate both sections with a line `/// # Struct`
The library code can be used with `#![no_std]`.
Because of limitations in rust, it is currently not possible to implement a “named future” for
generic functions: “error: generic `Self` types are currently not permitted in anonymous constants”.
Inspired by the prior work of Jun Ryung Ju: [`rename-future`]
[`Future`]: https://doc.rust-lang.org/1.65.0/core/future/trait.Future.html
[`Box<…>`]: https://doc.rust-lang.org/1.65.0/alloc/boxed/struct.Box.html
[`dyn …`]: https://doc.rust-lang.org/1.65.0/std/keyword.dyn.html
[`impl …`]: https://doc.rust-lang.org/1.65.0/std/keyword.impl.html
[`Send`]: https://doc.rust-lang.org/1.65.0/core/marker/trait.Send.html
[`Sync`]: https://doc.rust-lang.org/1.65.0/core/marker/trait.Sync.html
[tait]: https://github.com/rust-lang/rust/issues/63063
[rfc1598]: https://github.com/rust-lang/rfcs/blob/master/text/1598-generic_associated_types.md
[`rename-future`]: https://github.com/ArtBlnd/rename-future/tree/20c9d44726fd9f148f118cc260b713ce3d609ba2