pavex/blueprint/prebuilt.rs
1use pavex_bp_schema::{Blueprint as BlueprintSchema, Component, PrebuiltType};
2
3use crate::blueprint::{CloningPolicy, conversions::cloning2cloning};
4
5use super::reflection::AnnotationCoordinates;
6
7/// The input type for [`Blueprint::prebuilt`].
8///
9/// Check out [`Blueprint::prebuilt`] for more information on prebuilt types
10/// in Pavex.
11///
12/// # Stability guarantees
13///
14/// Use the [`prebuilt`](macro@crate::prebuilt) attribute macro to create instances of `Prebuilt`.\
15/// `Prebuilt`'s fields are an implementation detail of Pavex's macros and should not be relied upon:
16/// newer versions of Pavex may add, remove or modify its fields.
17///
18/// [`Blueprint::prebuilt`]: crate::Blueprint::prebuilt
19pub struct Prebuilt {
20 #[doc(hidden)]
21 pub coordinates: AnnotationCoordinates,
22}
23
24/// The type returned by [`Blueprint::prebuilt`].
25///
26/// It allows you to further configure the behaviour of the registered prebuilt type.
27///
28/// [`Blueprint::prebuilt`]: crate::Blueprint::prebuilt
29pub struct RegisteredPrebuilt<'a> {
30 #[allow(unused)]
31 pub(crate) blueprint: &'a mut BlueprintSchema,
32 /// The index of the registered prebuilt type in the blueprint's `components` vector.
33 #[allow(unused)]
34 pub(crate) component_id: usize,
35}
36
37impl RegisteredPrebuilt<'_> {
38 /// Set the cloning strategy for the output type returned by this constructor.
39 ///
40 /// By default,
41 /// Pavex will **never** try to clone a prebuilt type.
42 /// If the type implements [`Clone`], you can change the default by invoking
43 /// [`clone_if_necessary`](Self::clone_if_necessary): Pavex will clone the prebuilt type if
44 /// it's necessary to generate code that satisfies Rust's borrow checker.
45 pub fn cloning(mut self, strategy: CloningPolicy) -> Self {
46 self.prebuilt().cloning_policy = Some(cloning2cloning(strategy));
47 self
48 }
49
50 /// Set the cloning strategy to [`CloningPolicy::CloneIfNecessary`].
51 /// Check out [`cloning`](Self::cloning) method for more details.
52 pub fn clone_if_necessary(self) -> Self {
53 self.cloning(CloningPolicy::CloneIfNecessary)
54 }
55
56 /// Set the cloning strategy to [`CloningPolicy::NeverClone`].
57 /// Check out [`cloning`](Self::cloning) method for more details.
58 pub fn never_clone(self) -> Self {
59 self.cloning(CloningPolicy::NeverClone)
60 }
61
62 fn prebuilt(&mut self) -> &mut PrebuiltType {
63 let component = &mut self.blueprint.components[self.component_id];
64 let Component::PrebuiltType(s) = component else {
65 unreachable!("The component should be a prebuilt type")
66 };
67 s
68 }
69}