Skip to content

benjaminhottell/rs-string-bundle

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

1 Commit
 
 
 
 
 
 
 
 
 
 

Repository files navigation

string-bundle

Provides a derive macro that enables ergonomic conversions for structs with string-like types.

Instead of writing code like this:

struct BorrowedData<'a> {
    value: &'a str,
    // ...
}

struct OwnedData {
    value: String,
    // ...
}

impl<'a> BorrowedData<'a> {
    pub fn to_owned_fields(&self) -> OwnedData {
        OwnedData {
            value: String::from(self.value),
            // ...
        }
    }
}

impl OwnedData {
    pub fn as_borrowed_fields<'a>(&'a self) -> BorrowedData<'a> {
        BorrowedData {
            value: self.value.as_str(),
            // ...
        }
    }
}

You can instead write:

use string_bundle::StringBundle;

#[derive(StringBundle)]
struct Data<S> {
    value: S
    // ...
}

let data = Data { value: "hello" };

// Automatically generated methods

let data2 = data.to_owned_fields();
assert_eq!(String::from("hello"), data2.value);

let data3 = data2.as_borrowed_fields();
assert_eq!("hello", data3.value);

Advanced usage

Overriding field inference

The macro can automatically detect S and Option<S>. See below:

#[derive(string_bundle::StringBundle)]
struct Data<S> {
    value1: S,
    value2: Option<S>,
    // ...
}

This automatic detection can be overridden if it is incorrect, or to enable more complex behavior.

#[derive(string_bundle::StringBundle)]
struct SubData<S> {
    value: S,
    // ...
}

#[derive(string_bundle::StringBundle)]
struct Data<S> {

    // Manually specifying inferred behavior
    #[bundle(field)]
    value1: S,
    #[bundle(option_field)]
    value2: Option<S>,

    // Specifying advanced behavior
    #[bundle(nest)]
    sub_data1: SubData<S>,
    #[bundle(option_nest)]
    sub_data2: Option<SubData<S>>,
    #[bundle(default)]
    marker: std::marker::PhantomData<S>,
    #[bundle(clone)]
    number: u32,
    #[bundle(skip)]
    red_herring: String,
}

The advanced kinds of bundle fields are:

nest: Forward mapping requests to another string bundle. This allows you to recursively define string bundles.

option_nest: Forward mapping requests to another, contained string bundle that is wrapped in an Option.

default: Always call Default::default for this field instead of applying mapping functions or referencing it. (Suitable for marker types, unit structs, etc.)

clone: Always clone this field instead of applying mapping functions or referencing it. May degrade performance if cloning is not cheap.

skip: Ignore requests to map this field, pass it along as-is. (Warning: This field disables the as_ref_fields function because skip fields cannot be referenced)

About

Derive macro for quickly converting string-like fields within a struct

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Languages