| Crates.io | serde_yml |
| lib.rs | serde_yml |
| version | 0.0.12 |
| created_at | 2024-03-29 13:47:41.460002+00 |
| updated_at | 2024-08-25 16:06:09.793708+00 |
| description | A robust Rust library that simplifies the serialization and deserialization of Rust data structures to and from YAML format using the widely-used Serde framework. |
| homepage | https://serdeyml.com |
| repository | https://github.com/sebastienrousseau/serde_yml |
| max_upload_size | |
| id | 1190091 |
| size | 829,172 |
Serde YML is a Rust library for using the Serde serialization framework with data in YAML file format.
!tag syntax for representing enum variantsValue type and related types like Mapping and SequenceError, Location, and Result typesto_string and to_writer functionsfrom_str, from_slice, and from_reader functions#[serde(with = ...)] attributesingleton_map modulesingleton_map serialization/deserialization to all enums within a data structure using the singleton_map_recursive modulesingleton_map_optional modulesingleton_map_recursive modulesingleton_map_with module and custom helper functionsAdd this to your Cargo.toml:
[dependencies]
serde = "1.0"
serde_yml = "0.0.12"
Here's a quick example on how to use Serde YML to serialize and deserialize a struct to and from YAML:
use serde::{Serialize, Deserialize};
#[derive(Serialize, Deserialize)]
struct Point {
x: f64,
y: f64,
}
fn main() -> Result<(), serde_yml::Error> {
let point = Point { x: 1.0, y: 2.0 };
// Serialize to YAML
let yaml = serde_yml::to_string(&point)?;
assert_eq!(yaml, "x: 1.0\ny: 2.0\n");
// Deserialize from YAML
let deserialized_point: Point = serde_yml::from_str(&yaml)?;
assert_eq!(point, deserialized_point);
Ok(())
}
For full API documentation, please visit https://doc.libyml.com/serde-yaml/ or https://docs.rs/serde-yaml.
Compiler support: requires rustc 1.56.0+
Serde YML provides a set of comprehensive examples. You can find them in the
examples directory of the project. To run the examples, clone the repository
and execute the following command in your terminal from the project:
cargo run --example example
The examples cover various scenarios, including serializing and deserializing structs, enums, optional fields, custom structs, and more.
Here are a few notable examples:
use serde::{Serialize, Deserialize};
use serde_yml;
#[derive(Serialize, Deserialize, PartialEq, Debug)]
struct Point {
x: f64,
y: f64,
}
fn main() -> Result<(), serde_yml::Error> {
let point = Point { x: 1.0, y: 2.0 };
// Serialize to YAML
let yaml = serde_yml::to_string(&point)?;
assert_eq!(yaml, "x: 1.0\ny: 2.0\n");
// Deserialize from YAML
let deserialized_point: Point = serde_yml::from_str(&yaml)?;
assert_eq!(point, deserialized_point);
Ok(())
}
This example demonstrates how to serialize and deserialize a simple struct
Point to and from YAML using the serde_yml crate.
use serde::{Serialize, Deserialize};
use serde_yml;
#[derive(Serialize, Deserialize, PartialEq, Debug)]
enum Shape {
Rectangle { width: u32, height: u32 },
Circle { radius: f64 },
Triangle { base: u32, height: u32 },
}
fn main() -> Result<(), serde_yml::Error> {
let shapes = vec![
Shape::Rectangle { width: 10, height: 20 },
Shape::Circle { radius: 5.0 },
Shape::Triangle { base: 8, height: 12 },
];
// Serialize to YAML
let yaml = serde_yml::to_string(&shapes)?;
println!("Serialized YAML:\n{}", yaml);
// Deserialize from YAML
let deserialized_shapes: Vec<Shape> = serde_yml::from_str(&yaml)?;
assert_eq!(shapes, deserialized_shapes);
Ok(())
}
This example demonstrates how to serialize and deserialize an enum Shape
(with struct variants) to and from YAML using the serde_yml crate.
use serde::{Serialize, Deserialize};
use serde_yml;
#[derive(Serialize, Deserialize, PartialEq, Debug)]
struct User {
name: String,
age: Option<u32>,
#[serde(default)]
is_active: bool,
}
fn main() -> Result<(), serde_yml::Error> {
let user = User {
name: "John".to_string(),
age: Some(30),
is_active: true,
};
// Serialize to YAML
let yaml = serde_yml::to_string(&user)?;
println!("Serialized YAML:\n{}", yaml);
// Deserialize from YAML
let deserialized_user: User = serde_yml::from_str(&yaml)?;
assert_eq!(user, deserialized_user);
Ok(())
}
This example demonstrates how to serialize and deserialize a struct User with
an optional field age to and from YAML using the serde_yml crate.
use std::collections::HashMap;
use serde_yml;
fn main() -> Result<(), serde_yml::Error> {
let mut map = HashMap::new();
map.insert("name".to_string(), "John".to_string());
map.insert("age".to_string(), "30".to_string());
let yaml = serde_yml::to_string(&map)?;
println!("Serialized YAML: {}", yaml);
let deserialized_map: HashMap<String, serde_yml::Value> = serde_yml::from_str(&yaml)?;
println!("Deserialized map: {:?}", deserialized_map);
Ok(())
}
This example demonstrates how to serialize and deserialize a HashMap to and
from YAML using the serde_yml crate.
use serde::{Serialize, Deserialize};
use serde_yml;
#[derive(Serialize, Deserialize, Debug)]
struct Person {
name: String,
age: u32,
city: String,
}
fn main() -> Result<(), serde_yml::Error> {
let person = Person {
name: "Alice".to_string(),
age: 25,
city: "New York".to_string(),
};
let yaml = serde_yml::to_string(&person)?;
println!("Serialized YAML: {}", yaml);
let deserialized_person: Person = serde_yml::from_str(&yaml)?;
println!("Deserialized person: {:?}", deserialized_person);
Ok(())
}
This example demonstrates how to serialize and deserialize a custom struct
Person to and from YAML using the serde_yml crate.
It can also be used with Serde's derive macros to handle structs and enums defined in your program.
Structs serialize in the obvious way:
use serde_derive::{Serialize, Deserialize};
use serde_yml;
#[derive(Serialize, Deserialize, PartialEq, Debug)]
struct Point {
x: f64,
y: f64,
}
fn main() -> Result<(), serde_yml::Error> {
let point = Point { x: 1.0, y: 2.0 };
let yaml = serde_yml::to_string(&point)?;
assert_eq!(yaml, "x: 1.0\n'y': 2.0\n");
let deserialized_point: Point = serde_yml::from_str(&yaml)?;
assert_eq!(point, deserialized_point);
Ok(())
}
Enums serialize using YAML's !tag syntax to identify the variant name.
use serde_derive::{Serialize, Deserialize};
use serde_yml;
#[derive(Serialize, Deserialize, PartialEq, Debug)]
enum Enum {
Unit,
Newtype(usize),
Tuple(usize, usize, usize),
Struct { x: f64, y: f64 },
}
fn main() -> Result<(), serde_yml::Error> {
let yaml = "
- !Newtype 1
- !Tuple [0, 0, 0]
- !Struct {x: 1.0, y: 2.0}
";
let values: Vec<Enum> = serde_yml::from_str(yaml).unwrap();
assert_eq!(values[0], Enum::Newtype(1));
assert_eq!(values[1], Enum::Tuple(0, 0, 0));
assert_eq!(values[2], Enum::Struct { x: 1.0, y: 2.0 });
// The last two in YAML's block style instead:
let yaml = "
- !Tuple
- 0
- 0
- 0
- !Struct
x: 1.0
'y': 2.0
";
let values: Vec<Enum> = serde_yml::from_str(yaml).unwrap();
assert_eq!(values[0], Enum::Tuple(0, 0, 0));
assert_eq!(values[1], Enum::Struct { x: 1.0, y: 2.0 });
// Variants with no data can be written using !Tag or just the string name.
let yaml = "
- Unit # serialization produces this one
- !Unit
";
let values: Vec<Enum> = serde_yml::from_str(yaml).unwrap();
assert_eq!(values[0], Enum::Unit);
assert_eq!(values[1], Enum::Unit);
Ok(())
}
This example demonstrates how to use Serde's derive macros to automatically
implement the Serialize and Deserialize traits for a struct Point, and
then serialize and deserialize it to and from YAML using the serde_yml crate.
use serde::{Deserialize, Serialize};
use serde::de::{self, Deserializer, MapAccess, Visitor};
use serde::ser::{SerializeMap, Serializer};
use std::fmt;
use serde_yml;
#[derive(Serialize, Deserialize, PartialEq, Debug)]
enum MyEnum {
Variant1(String),
Variant2 { field: i32 },
}
#[derive(PartialEq, Debug)]
struct MyStruct {
field: MyEnum,
}
// Include custom Serialize and Deserialize implementations for MyStruct here
// ...
fn main() -> Result<(), serde_yml::Error> {
let input = MyStruct {
field: MyEnum::Variant2 { field: 42 },
};
let yaml = serde_yml::to_string(&input).unwrap();
println!("\n✅ Serialized YAML:\n{}", yaml);
let output: MyStruct = serde_yml::from_str(&yaml).unwrap();
println!("\n✅ Deserialized YAML:\n{:#?}", output);
assert_eq!(input, output);
Ok(())
}
This example demonstrates how to use custom Serialize and Deserialize
implementations for a struct containing an enum field, and how to leverage
serde_yml to serialize and deserialize the struct to and from YAML.
use serde::{Deserialize, Serialize};
use serde_yml;
use serde_yml::with::singleton_map_optional;
#[derive(Serialize, Deserialize, PartialEq, Debug)]
enum OptionalEnum {
Variant1(String),
Variant2 { field: i32 },
}
#[derive(Serialize, Deserialize, PartialEq, Debug)]
struct OptionalStruct {
#[serde(with = "singleton_map_optional")]
field: Option<OptionalEnum>,
}
fn main() -> Result<(), serde_yml::Error> {
let input = OptionalStruct {
field: Some(OptionalEnum::Variant2 { field: 42 }),
};
let yaml = serde_yml::to_string(&input).unwrap();
println!("\n✅ Serialized YAML:\n{}", yaml);
let output: OptionalStruct = serde_yml::from_str(&yaml).unwrap();
println!("\n✅ Deserialized YAML:\n{:#?}", output);
assert_eq!(input, output);
Ok(())
}
This example demonstrates how to use the singleton_map_optional
attribute to serialize and deserialize an Option<Enum> field as a single
YAML mapping entry with the key being the enum variant name.
use serde::{Deserialize, Serialize};
use serde_yml;
use serde_yml::with::singleton_map_recursive;
#[derive(Serialize, Deserialize, PartialEq, Debug)]
enum NestedEnum {
Variant1(String),
Variant2(Option<InnerEnum>),
}
#[derive(Serialize, Deserialize, PartialEq, Debug)]
enum InnerEnum {
Inner1(i32),
Inner2(i32),
}
#[derive(Serialize, Deserialize, PartialEq, Debug)]
struct NestedStruct {
#[serde(with = "singleton_map_recursive")]
field: NestedEnum,
}
fn main() -> Result<(), serde_yml::Error> {
let input = NestedStruct {
field: NestedEnum::Variant2(Some(InnerEnum::Inner2(42))),
};
let yaml = serde_yml::to_string(&input).unwrap();
println!("\n✅ Serialized YAML:\n{}", yaml);
let output: NestedStruct = serde_yml::from_str(&yaml).unwrap();
println!("\n✅ Deserialized YAML:\n{:#?}", output);
assert_eq!(input, output);
Ok(())
}
This example demonstrates how to use the singleton_map_recursive attribute to
serialize and deserialize a nested enum structure where one of the enum
variants contains an optional inner enum.
singleton_map_recursiveuse serde::{Deserialize, Serialize};
use serde_yml;
use serde_yml::with::singleton_map_recursive;
#[derive(Serialize, Deserialize, PartialEq, Debug)]
enum MyEnum {
Variant1(String),
Variant2 { field: i32 },
}
#[derive(Serialize, Deserialize, PartialEq, Debug)]
struct MyStruct {
#[serde(with = "singleton_map_recursive")]
field: MyEnum,
}
fn main() -> Result<(), serde_yml::Error> {
let input = MyStruct {
field: MyEnum::Variant2 { field: 42 },
};
let yaml = serde_yml::to_string(&input).unwrap();
println!("\n✅ Serialized YAML:\n{}", yaml);
let output: MyStruct = serde_yml::from_str(&yaml).unwrap();
println!("\n✅ Deserialized YAML:\n{:#?}", output);
assert_eq!(input, output);
Ok(())
}
This example demonstrates how to use the singleton_map_recursive attribute to
serialize and deserialize an enum field as a single YAML mapping entry with the
key being the enum variant name.
singleton_map_with and Custom Serializationuse serde::{Deserialize, Serialize};
use serde_yml;
use serde_yml::with::singleton_map_with;
fn custom_serialize<T, S>(
value: &T,
serializer: S,
) -> Result<S::Ok, S::Error>
where
T: Serialize,
S: serde::Serializer,
{
// Custom serialization logic
singleton_map_with::serialize(value, serializer)
}
#[derive(Serialize, Deserialize, PartialEq, Debug)]
enum MyEnum {
Variant1(String),
Variant2 { field: i32 },
}
#[derive(Serialize, Deserialize, PartialEq, Debug)]
struct MyStruct {
#[serde(
serialize_with = "custom_serialize",
deserialize_with = "singleton_map_with::deserialize"
)]
field: MyEnum,
}
fn main() -> Result<(), serde_yml::Error> {
let input = MyStruct {
field: MyEnum::Variant2 { field: 42 },
};
let yaml = serde_yml::to_string(&input).unwrap();
println!("\n✅ Serialized YAML:\n{}", yaml);
let output: MyStruct = serde_yml::from_str(&yaml).unwrap();
println!("\n✅ Deserialized YAML:\n{:#?}", output);
assert_eq!(input, output);
Ok(())
}
This example demonstrates how to use the singleton_map_with attribute in
combination with a custom serialization function (custom_serialize) to
serialize and deserialize an enum field (MyEnum) within a struct
(MyStruct).
The custom_serialize function is used for serialization, while the
singleton_map_with::deserialize function is used for deserialization. This
allows for additional customization of the serialization process while still
leveraging the singleton_map_with attribute for deserialization.
singleton_map_withuse serde::{Deserialize, Serialize};
use serde_yml;
use serde_yml::with::singleton_map_with;
#[derive(Serialize, Deserialize, PartialEq, Debug)]
enum MyEnum {
Variant1(String),
Variant2 { field: i32 },
}
#[derive(Serialize, Deserialize, PartialEq, Debug)]
struct MyStruct {
#[serde(with = "singleton_map_with")]
field: MyEnum,
}
fn main() -> Result<(), serde_yml::Error> {
let input = MyStruct {
field: MyEnum::Variant2 { field: 42 },
};
let yaml = serde_yml::to_string(&input).unwrap();
println!("\n✅ Serialized YAML:\n{}", yaml);
let output: MyStruct = serde_yml::from_str(&yaml).unwrap();
println!("\n✅ Deserialized YAML:\n{:#?}", output);
assert_eq!(input, output);
Ok(())
}
This example demonstrates how to use the singleton_map_with attribute to
serialize and deserialize an enum field (MyEnum) within a struct
(MyStruct). The singleton_map_with attribute allows for additional
customization of the serialization and deserialization process through the use
of helper functions.
Contributions are welcome! Please submit a Pull Request on GitHub.
Serde YML is a continuation of the excellent work done by David Tolnay and the maintainers of the serde-yaml library. While Serde YML has evolved into a separate library, we express our sincere gratitude to them for their contributions to the Rust community.
Licensed under either of the Apache License or the MIT license at your option.
Unless you explicitly state otherwise, any contribution intentionally submitted for inclusion in this crate by you, as defined in the Apache-2.0 license, shall be dual licensed as above, without any additional terms or conditions.