compost/
lib.rs

1//! # Overview
2//!
3//! This library exposes [`decompose!`](crate::decompose), a macro to decompose tuples into tuples
4//! containing a subset of their values.
5//!
6//! ```
7//! use compost::decompose;
8//!
9//! // Pack all your context into a tuple...
10//! let mut cx = (&mut 1u32, &2u8, (&3u16, &mut 'e', "f", &mut [1, 2, 3]));
11//!
12//! // And cal your target function!
13//! consumer(decompose!(cx));
14//!
15//! // Define functions taking tuples of context...
16//! fn consumer_2((a, b, c, d, e): (&u32, &str, &char, &f32, &i8)) {
17//!     dbg!(a, b, c, d, e);
18//! }
19//!
20//! fn consumer_3((f, g, h): (&char, &str, &mut [u8; 3])) {
21//!     dbg!(f, g, h);
22//! }
23//!
24//! fn consumer(mut cx: (&mut u32, &char, &str, &mut [u8; 3])) {
25//!     // Bring types into scope and produce a remainder tuple.
26//!     decompose!(cx => rest & {
27//!         char: &char,
28//!         bytes: &mut [u8; 3],
29//!     });
30//!
31//!     // Combine contexts...
32//!     let mut rest = (rest, (&mut 4.3f32, &-4i8), &mut 5i16);
33//!
34//!     // ...and forward them to further functions.
35//!     consumer_2(decompose!(rest));
36//!
37//!     // ...all without invalidating existing borrows!
38//!     dbg!(char, bytes);
39//!
40//!     // Reborrow the original context after its borrows have expired.
41//!     consumer_3(decompose!(cx));
42//! }
43//! ```
44//!
45//! See [`decompose!`](crate::decompose)'s documentation for more details on the precise semantics and
46//! limitations of the macro.
47//!
48//! ## Features
49//!
50//! Yes, this library...
51//!
52//! - Supports reborrowing (i.e. `decompose!` does not consume its input. Once you're done
53//!    with the borrow, you can reuse the original tuple).
54//! - Produces (admittedly pretty ugly) errors at compile time if the tuple cannot be decomposed.
55//! - Supports borrowing mutable, immutable, and smart-pointer wrapped (so long as they implement
56//!   [`Deref`](::core::ops::Deref)) components.
57//! - Supports borrowing from nested tuple trees, allowing you to borrow from an arbitrary number of
58//!   components simultaneously and to quickly merge multiple context tuples by packing them into a
59//!   single tuple.
60//! - Supports borrowing generic elements without failing spuriously on monomorphization.
61//! - Relies on type inference rather than `TypeId`, allowing the macro to operate on non-`'static` types.
62//! - Supports `no_std` environments and does not rely on unsafe code.
63//! - Has zero runtime dependencies.
64//!
65
66#![no_std]
67#![forbid(unsafe_code)]
68
69// Necessary to avoid ambiguous doc link to `crate::decompose`.
70#[path = "decompose.rs"]
71mod decompose_impl;
72
73#[doc(hidden)]
74pub mod macro_internal {
75    pub use super::decompose_impl::*;
76    pub use core::option::Option::{None, Some};
77}