#[staged_builder]Expand description
Creates a staged builder interface for structs.
The macro will create a submodule with the snake_case version of the type’s name containing the builder types, and
add a builder constructor function to the type. Each required field of the struct will correspond to a builder
type named after it, with an additional “final” stage to set optional fields and construct the final value.
By default, all fields are considered required and their setters will simply take their declared type by-value. This behavior can be customized with field options.
§Struct options
Options can be applied at the struct level via the #[builder(...)] attribute as a comma-separated sequence:
validate- The finalbuildmethod will return aResult, calling the type’sValidateimplementation before returning the constructed value.update- The completed stage of the builder will have setters for all fields, and aFromimpl will be created to allow an instance of the struct to be converted back into the builder type for further updates.crate- Indicates the path to thestaged_buildercrate root. Useful when reexporting the macro from another crate. Defaults to::staged_builder.mod- The name of the submodule that will contain the generated builder types. Defaults to the struct’s name converted tosnake_case.inline- Causes the generated builder types to be defined in the same module as the struct, rather than a submodule.builder- Sets the name of the generated builder type. Defaults toBuilder.complete- Sets the name of the generated complete stage type. Defaults toComplete.
§Field options
Options can be applied to individual fields via the #[builder(...)] attribute as a comma-separated sequence:
default- Causes the field to be considered optional. TheDefaulttrait is normally used to generate the default field value. A custom default can be specified withdefault = <expr>, where<expr>is an expression.into- Causes the setter method for the field to takeimpl Into<FieldType>rather thanFieldTypedirectly.custom- Causes the setter method to perform an arbitrary conversion for the field. The option expects atypewhich will be used as the argument type in the setter, and aconvertcallable expression which will be invoked by the setter. For example, the annotation#[builder(into)]on a field of typeTis equivalent to the annotation#[builder(custom(type = impl Into<T>, convert = Into::into))].list- Causes the field to be treated as a “list style” type. It will default to an empty collection, and three setter methods will be generated:push_footo add a single value,footo set the contents, andextend_footo exend the collection with new values. The underlying type must have apushmethod, aFromIteratorimplementation, and anExtendimplementation. The item type must be configured in the attribute:#[builder(list(item(type = YourItemType)))].set- Causes the field to be treated as a “set style” type. It will default to an empty collection, and three setter methods will be generated:insert_footo add a single value,footo set the contents, andextend_footo exend the collection with new values. The underlying type must have aninsertmethod, aFromIteratorimplementation, and anExtendimplementation. The item type must be configured in the attribute:#[builder(set(item(type = YourItemType)))].map- Causes the field to be treated as a “map style” type. It will default to an empty collection, and three setter methods will be generated:insert_footo add a single entry,footo set the contents, andextend_footo exend the collection with new entries. The underlying type must have aninsertmethod, aFromIteratorimplementation, and anExtendimplementation. The key and value types must be configured in the attribute:#[builder(map(key(type = YourKeyType), value(type = YourValueType)))].stage- Sets the name of the generated stage type. Defaults to the name of the field converted toPascalCasewithStageappended.
§Collection type options
Options can be applied to the item types of collections as a comma-separated sequence:
type- Indicates the type of the item in the collection. Required unless usingcustom.into- Causes setter methods to takeimpl<Into<ItemType>>rather thanItemTypedirectly.custom- Causes the setter methods to perform an arbitrary conversion for the field.
§Example expansion
use staged_builder::staged_builder;
#[staged_builder]
pub struct MyStruct {
required_field: u32,
#[builder(into)]
into_required_field: String,
#[builder(default)]
standard_optional_field: bool,
#[builder(default = "foobar".to_string())]
custom_default_field: String,
#[builder(list(item(type = i32)))]
list_field: Vec<i32>,
}Will expand into:
pub struct MyStruct {
required_field: u32,
into_required_field: String,
standard_optional_field: bool,
custom_default_field: String,
list_field: Vec<i32>,
}
impl MyStruct {
pub fn builder() -> my_struct::Builder<my_struct::RequiredFieldStage> {
// ...
}
}
pub mod my_struct {
pub struct Builder<T> {
// ...
}
impl Default for Builder<RequiredFieldStage> {
fn default() -> Self {
// ...
}
}
impl Builder<RequiredFieldStage> {
pub fn required_field(self, required_field: u32) -> Builder<IntoRequiredFieldStage> {
// ...
}
}
impl Builder<IntoRequiredFieldStage> {
pub fn into_required_field(self, into_required_field: impl Into<String>) -> Builder<FinalStage> {
// ...
}
}
impl Builder<FinalStage> {
pub fn standard_optional_field(self, standard_optional_field: bool) -> Self {
// ...
}
pub fn custom_default_field(self, custom_default_field: String) -> Self {
// ...
}
pub fn push_list_field(self, list_field: i32) -> Self {
// ...
}
pub fn list_field(self, list_field: impl IntoIterator<Item = i32>) -> Self {
// ...
}
pub fn extend_list_field(self, list_field: impl IntoIterator<Item = i32>) -> Self {
// ...
}
pub fn build(self) -> super::MyStruct {
// ...
}
}
pub struct RequiredFieldStage {
// ...
}
pub struct IntoRequiredFieldStage {
// ...
}
pub struct FinalStage {
// ...
}
}