#serialization #no-std

no-std valuable

Object-safe value inspection, used to pass un-typed structured data across trait-object boundaries

2 unstable releases

0.1.0 Jan 3, 2022
0.0.0 Mar 9, 2021

#672 in Debugging

Download history 464022/week @ 2023-10-18 472213/week @ 2023-10-25 494704/week @ 2023-11-01 482753/week @ 2023-11-08 468172/week @ 2023-11-15 350971/week @ 2023-11-22 416086/week @ 2023-11-29 421039/week @ 2023-12-06 457957/week @ 2023-12-13 326995/week @ 2023-12-20 272781/week @ 2023-12-27 481497/week @ 2024-01-03 508742/week @ 2024-01-10 522292/week @ 2024-01-17 503618/week @ 2024-01-24 437037/week @ 2024-01-31

2,064,673 downloads per month
Used in 6,807 crates (23 directly)

MIT license

130KB
1.5K SLoC

Valuable

Valuable provides object-safe value inspection. Use cases include passing structured data to trait objects and object-safe serialization.

License

This project is licensed under the MIT license.

Contribution

Unless you explicitly state otherwise, any contribution intentionally submitted for inclusion in Valuable by you, shall be licensed as MIT, without any additional terms or conditions.


lib.rs:

Valuable provides object-safe value inspection. Use cases include passing structured data to trait objects and object-safe serialization.

Getting started

First, derive [Valuable][macro@crate::Valuable] on your types.

use valuable::Valuable;

#[derive(Valuable)]
struct HelloWorld {
    message: Message,
}

#[derive(Valuable)]
enum Message {
    HelloWorld,
    Custom(String),
}

Then, implement a [visitor][Visit] to inspect the data.

use valuable::{NamedValues, Value, Valuable, Visit};

struct Print;

impl Visit for Print {
    fn visit_value(&mut self, value: Value<'_>) {
        match value {
            Value::Structable(v) => {
                println!("struct {}", v.definition().name());
                v.visit(self);
            }
            Value::Enumerable(v) => {
                println!("enum {}::{}", v.definition().name(), v.variant().name());
                v.visit(self);
            }
            Value::Listable(v) => {
                println!("list");
                v.visit(self);
            }
            Value::Mappable(v) => {
                println!("map");
                v.visit(self);
            }
            _ => {
                println!("value {:?}", value);
            }
        }
    }

    fn visit_named_fields(&mut self, named_fields: &NamedValues<'_>) {
        for (field, value) in named_fields.iter() {
            println!("named field {}", field.name());
            value.visit(self);
        }
    }

    fn visit_unnamed_fields(&mut self, values: &[Value<'_>]) {
        for value in values {
            value.visit(self);
        }
    }

    fn visit_entry(&mut self, key: Value<'_>, value: Value<'_>) {
        println!("key / value");
        key.visit(self);
        value.visit(self);
    }
}

Then, use the visitor to visit the value.

let hello_world = HelloWorld { message: Message::HelloWorld };
hello_world.visit(&mut Print);

Dependencies

~195KB