use serde::{Deserialize, Serialize};
use std::collections::HashMap;
use std::io::Cursor;
#[derive(Serialize, Deserialize, Debug, PartialEq)]
struct Point {
x: f64,
y: f64,
}
#[derive(Serialize, Deserialize, Debug, PartialEq)]
struct ScalarFields {
a: bool,
b: u32,
c: i64,
d: f32,
e: String,
}
#[derive(Serialize, Deserialize, Debug, PartialEq)]
struct Nested {
name: String,
point: Point,
tags: Vec<String>,
}
#[derive(Serialize, Deserialize, Debug, PartialEq)]
enum Color {
Red,
Green,
Blue,
}
#[derive(Serialize, Deserialize, Debug, PartialEq)]
enum Shape {
Circle(f64),
Rect { w: f64, h: f64 },
Triangle(f64, f64, f64),
Point,
}
#[derive(Serialize, Deserialize, Debug, PartialEq)]
struct WithOptional {
a: Option<u32>,
b: Option<u32>,
}
#[derive(Serialize, Deserialize, Debug, PartialEq)]
struct Empty {}
#[test]
fn streaming_scalar_struct_matches_to_vec() {
let p = Point { x: 1.0, y: -2.5 };
let expected = beve::to_vec(&p).unwrap();
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &p).unwrap();
assert_eq!(buf, expected);
}
#[test]
fn streaming_scalar_fields_match_to_vec() {
let v = ScalarFields {
a: true,
b: 42,
c: -100,
d: 1.5,
e: "hello".into(),
};
let expected = beve::to_vec(&v).unwrap();
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
assert_eq!(buf, expected);
}
#[test]
fn streaming_round_trip_point() {
let p = Point { x: 1.0, y: -2.5 };
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &p).unwrap();
let p2: Point = beve::from_slice(&buf).unwrap();
assert_eq!(p, p2);
}
#[test]
fn streaming_round_trip_nested() {
let n = Nested {
name: "test".into(),
point: Point { x: 0.0, y: 1.0 },
tags: vec!["a".into(), "b".into(), "c".into()],
};
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &n).unwrap();
let n2: Nested = beve::from_slice(&buf).unwrap();
assert_eq!(n, n2);
}
#[test]
fn streaming_round_trip_hashmap_string_keys() {
let mut m = HashMap::new();
m.insert("x".to_string(), 1.0f64);
m.insert("y".to_string(), 2.0);
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &m).unwrap();
let m2: HashMap<String, f64> = beve::from_slice(&buf).unwrap();
assert_eq!(m, m2);
}
#[test]
fn streaming_round_trip_vec_string() {
let v = vec!["hello".to_string(), "world".to_string()];
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
let v2: Vec<String> = beve::from_slice(&buf).unwrap();
assert_eq!(v, v2);
}
#[test]
fn streaming_round_trip_vec_f64() {
let v = vec![1.0f64, 2.0, 3.0, 4.0, 5.0];
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
let v2: Vec<f64> = beve::from_slice(&buf).unwrap();
assert_eq!(v, v2);
}
#[test]
fn streaming_round_trip_vec_i32() {
let v = vec![10i32, -20, 30, -40];
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
let v2: Vec<i32> = beve::from_slice(&buf).unwrap();
assert_eq!(v, v2);
}
#[test]
fn streaming_round_trip_vec_bool() {
let v = vec![true, false, true, true, false];
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
let v2: Vec<bool> = beve::from_slice(&buf).unwrap();
assert_eq!(v, v2);
}
#[test]
fn streaming_round_trip_unit_variant() {
let c = Color::Green;
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &c).unwrap();
let c2: Color = beve::from_slice(&buf).unwrap();
assert_eq!(c, c2);
assert_eq!(buf, beve::to_vec(&c).unwrap());
}
#[test]
fn streaming_round_trip_newtype_variant() {
let s = Shape::Circle(2.5);
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &s).unwrap();
let s2: Shape = beve::from_slice(&buf).unwrap();
assert_eq!(s, s2);
}
#[test]
fn streaming_round_trip_struct_variant() {
let s = Shape::Rect { w: 3.0, h: 4.0 };
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &s).unwrap();
let s2: Shape = beve::from_slice(&buf).unwrap();
assert_eq!(s, s2);
}
#[test]
fn streaming_round_trip_tuple_variant() {
let s = Shape::Triangle(3.0, 4.0, 5.0);
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &s).unwrap();
let s2: Shape = beve::from_slice(&buf).unwrap();
assert_eq!(s, s2);
}
#[test]
fn streaming_round_trip_unit_variant_point() {
let s = Shape::Point;
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &s).unwrap();
let s2: Shape = beve::from_slice(&buf).unwrap();
assert_eq!(s, s2);
}
#[test]
fn streaming_round_trip_optional() {
let v = WithOptional {
a: Some(42),
b: None,
};
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
let v2: WithOptional = beve::from_slice(&buf).unwrap();
assert_eq!(v, v2);
assert_eq!(buf, beve::to_vec(&v).unwrap());
}
#[test]
fn streaming_round_trip_empty_struct() {
let e = Empty {};
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &e).unwrap();
let e2: Empty = beve::from_slice(&buf).unwrap();
assert_eq!(e, e2);
assert_eq!(buf, beve::to_vec(&e).unwrap());
}
#[test]
fn streaming_round_trip_empty_vec() {
let v: Vec<u32> = vec![];
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
let v2: Vec<u32> = beve::from_slice(&buf).unwrap();
assert_eq!(v, v2);
}
#[test]
fn streaming_round_trip_empty_map() {
let m: HashMap<String, u32> = HashMap::new();
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &m).unwrap();
let m2: HashMap<String, u32> = beve::from_slice(&buf).unwrap();
assert_eq!(m, m2);
}
#[test]
fn streaming_scalar_bool() {
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &true).unwrap();
let v: bool = beve::from_slice(&buf).unwrap();
assert!(v);
assert_eq!(buf, beve::to_vec(&true).unwrap());
}
#[test]
fn streaming_scalar_u64() {
let val = 12345u64;
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &val).unwrap();
let v: u64 = beve::from_slice(&buf).unwrap();
assert_eq!(v, val);
assert_eq!(buf, beve::to_vec(&val).unwrap());
}
#[test]
fn streaming_scalar_string() {
let val = "hello world".to_string();
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &val).unwrap();
let v: String = beve::from_slice(&buf).unwrap();
assert_eq!(v, val);
assert_eq!(buf, beve::to_vec(&val).unwrap());
}
#[test]
fn streaming_scalar_none() {
let val: Option<u32> = None;
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &val).unwrap();
let v: Option<u32> = beve::from_slice(&buf).unwrap();
assert_eq!(v, val);
assert_eq!(buf, beve::to_vec(&val).unwrap());
}
#[test]
fn streaming_scalar_unit() {
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &()).unwrap();
assert_eq!(buf, beve::to_vec(&()).unwrap());
}
#[test]
fn streaming_rejects_unknown_length_seq() {
struct UnknownLen;
impl Serialize for UnknownLen {
fn serialize<S: serde::Serializer>(&self, s: S) -> std::result::Result<S::Ok, S::Error> {
use serde::ser::SerializeSeq;
let mut seq = s.serialize_seq(None)?;
seq.serialize_element(&1u32)?;
seq.end()
}
}
let mut buf = Vec::new();
let result = beve::to_writer_streaming(&mut buf, &UnknownLen);
assert!(result.is_err());
let err_msg = result.unwrap_err().to_string();
assert!(err_msg.contains("known-length"), "got: {err_msg}");
}
#[test]
fn streaming_rejects_unknown_length_map() {
struct UnknownLenMap;
impl Serialize for UnknownLenMap {
fn serialize<S: serde::Serializer>(&self, s: S) -> std::result::Result<S::Ok, S::Error> {
use serde::ser::SerializeMap;
let mut map = s.serialize_map(None)?;
map.serialize_entry("k", &1u32)?;
map.end()
}
}
let mut buf = Vec::new();
let result = beve::to_writer_streaming(&mut buf, &UnknownLenMap);
assert!(result.is_err());
let err_msg = result.unwrap_err().to_string();
assert!(err_msg.contains("known-length"), "got: {err_msg}");
}
#[test]
fn streaming_write_to_cursor() {
let p = Point { x: 1.0, y: -2.5 };
let cursor = Cursor::new(Vec::new());
beve::to_writer_streaming(cursor, &p).unwrap();
}
#[test]
fn streaming_enum_matches_the_buffered_encoder() {
let c = Color::Blue;
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &c).unwrap();
assert_eq!(buf, beve::to_vec(&c).unwrap());
}
#[test]
fn streaming_enum_round_trip() {
let c = Color::Green;
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &c).unwrap();
let c2: Color = beve::from_reader_streaming(std::io::Cursor::new(&buf)).unwrap();
assert_eq!(c, c2);
let s = Shape::Circle(2.5);
buf.clear();
beve::to_writer_streaming(&mut buf, &s).unwrap();
let s2: Shape = beve::from_reader_streaming(std::io::Cursor::new(&buf)).unwrap();
assert_eq!(s, s2);
let s = Shape::Rect { w: 3.0, h: 4.0 };
buf.clear();
beve::to_writer_streaming(&mut buf, &s).unwrap();
let s2: Shape = beve::from_reader_streaming(std::io::Cursor::new(&buf)).unwrap();
assert_eq!(s, s2);
let s = Shape::Triangle(3.0, 4.0, 5.0);
buf.clear();
beve::to_writer_streaming(&mut buf, &s).unwrap();
let s2: Shape = beve::from_reader_streaming(std::io::Cursor::new(&buf)).unwrap();
assert_eq!(s, s2);
let s = Shape::Point;
buf.clear();
beve::to_writer_streaming(&mut buf, &s).unwrap();
let s2: Shape = beve::from_reader_streaming(std::io::Cursor::new(&buf)).unwrap();
assert_eq!(s, s2);
}
#[test]
fn streaming_round_trip_u32_key_map() {
let mut m = HashMap::new();
m.insert(1u32, "one".to_string());
m.insert(2u32, "two".to_string());
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &m).unwrap();
let m2: HashMap<u32, String> = beve::from_slice(&buf).unwrap();
assert_eq!(m, m2);
}
#[test]
fn streaming_round_trip_i64_key_map() {
let mut m = HashMap::new();
m.insert(-1i64, 100u32);
m.insert(42i64, 200u32);
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &m).unwrap();
let m2: HashMap<i64, u32> = beve::from_slice(&buf).unwrap();
assert_eq!(m, m2);
}
#[test]
fn streaming_round_trip_vec_of_structs() {
let v = vec![
Point { x: 1.0, y: 2.0 },
Point { x: 3.0, y: 4.0 },
Point { x: 5.0, y: 6.0 },
];
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
let v2: Vec<Point> = beve::from_slice(&buf).unwrap();
assert_eq!(v, v2);
}
#[test]
fn streaming_round_trip_map_of_vecs() {
let mut m = HashMap::new();
m.insert("a".to_string(), vec![1.0f64, 2.0, 3.0]);
m.insert("b".to_string(), vec![4.0, 5.0]);
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &m).unwrap();
let m2: HashMap<String, Vec<f64>> = beve::from_slice(&buf).unwrap();
assert_eq!(m, m2);
}
#[test]
fn streaming_round_trip_tuple() {
let t = (42u32, "hello".to_string(), true);
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &t).unwrap();
let t2: (u32, String, bool) = beve::from_slice(&buf).unwrap();
assert_eq!(t, t2);
}
#[test]
fn streaming_round_trip_vec_u8() {
let data = vec![1u8, 2, 3, 4, 5];
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &data).unwrap();
let data2: Vec<u8> = beve::from_slice(&buf).unwrap();
assert_eq!(data, data2);
}
#[test]
fn streaming_output_validates() {
let n = Nested {
name: "test".into(),
point: Point { x: 1.0, y: 2.0 },
tags: vec!["a".into(), "b".into()],
};
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &n).unwrap();
beve::validate_slice(&buf).unwrap();
}
#[test]
fn streaming_vec_output_validates() {
let v = vec![1u32, 2, 3, 4, 5];
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
beve::validate_slice(&buf).unwrap();
}
#[test]
fn streaming_large_vec() {
let v: Vec<f64> = (0..10_000).map(|i| i as f64).collect();
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
beve::validate_slice(&buf).unwrap();
let v2: Vec<f64> = beve::from_slice(&buf).unwrap();
assert_eq!(v, v2);
}
#[test]
fn streaming_large_struct_vec() {
let v: Vec<Point> = (0..1_000)
.map(|i| Point {
x: i as f64,
y: -(i as f64),
})
.collect();
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
beve::validate_slice(&buf).unwrap();
let v2: Vec<Point> = beve::from_slice(&buf).unwrap();
assert_eq!(v, v2);
}
#[test]
fn streaming_writer_error_propagation() {
struct FailWriter;
impl std::io::Write for FailWriter {
fn write(&mut self, _buf: &[u8]) -> std::io::Result<usize> {
Err(std::io::Error::other("disk full"))
}
fn flush(&mut self) -> std::io::Result<()> {
Ok(())
}
}
let p = Point { x: 1.0, y: 2.0 };
let result = beve::to_writer_streaming(FailWriter, &p);
assert!(result.is_err());
let msg = result.unwrap_err().to_string();
assert!(msg.contains("disk full"), "got: {msg}");
}
#[test]
fn streaming_serializer_direct_usage() {
use beve::StreamingSerializer;
use serde::Serialize;
let mut buf = Vec::new();
let mut ser = StreamingSerializer::new(&mut buf);
let p = Point { x: 1.0, y: 2.0 };
p.serialize(&mut ser).unwrap();
let p2: Point = beve::from_slice(&buf).unwrap();
assert_eq!(p, p2);
}
#[test]
fn streaming_typed_array_vec_f64_matches_to_vec() {
let v = vec![1.0f64, 2.0, 3.0, 4.0, 5.0];
let expected = beve::to_vec(&v).unwrap();
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
assert_eq!(buf, expected);
}
#[test]
fn streaming_typed_array_vec_f32_matches_to_vec() {
let v = vec![1.0f32, 2.0, 3.0];
let expected = beve::to_vec(&v).unwrap();
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
assert_eq!(buf, expected);
}
#[test]
fn streaming_typed_array_vec_u32_matches_to_vec() {
let v = vec![10u32, 20, 30, 40, 50];
let expected = beve::to_vec(&v).unwrap();
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
assert_eq!(buf, expected);
}
#[test]
fn streaming_typed_array_vec_u8_matches_to_vec() {
let v = vec![1u8, 2, 3, 4, 5];
let expected = beve::to_vec(&v).unwrap();
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
assert_eq!(buf, expected);
}
#[test]
fn streaming_typed_array_vec_i64_matches_to_vec() {
let v = vec![-100i64, 0, 100, 200];
let expected = beve::to_vec(&v).unwrap();
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
assert_eq!(buf, expected);
}
#[test]
fn streaming_typed_array_vec_i8_matches_to_vec() {
let v = vec![-1i8, 0, 1, 127, -128];
let expected = beve::to_vec(&v).unwrap();
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
assert_eq!(buf, expected);
}
#[test]
fn streaming_typed_array_vec_bool_matches_to_vec() {
let v = vec![true, false, true, true, false, false, true, false, true];
let expected = beve::to_vec(&v).unwrap();
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
assert_eq!(buf, expected);
}
#[test]
fn streaming_typed_array_vec_string_matches_to_vec() {
let v = vec!["hello".to_string(), "world".to_string(), "foo".to_string()];
let expected = beve::to_vec(&v).unwrap();
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
assert_eq!(buf, expected);
}
#[test]
fn streaming_typed_array_empty_vec_matches_to_vec() {
let v: Vec<f64> = vec![];
let expected = beve::to_vec(&v).unwrap();
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
assert_eq!(buf, expected);
}
#[test]
fn streaming_struct_with_typed_arrays_matches_to_vec() {
let n = Nested {
name: "test".into(),
point: Point { x: 1.0, y: 2.0 },
tags: vec!["a".into(), "b".into(), "c".into()],
};
let expected = beve::to_vec(&n).unwrap();
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &n).unwrap();
assert_eq!(buf, expected);
}
#[derive(Serialize, Deserialize, Debug, PartialEq)]
struct SciData {
label: String,
values: Vec<f64>,
flags: Vec<bool>,
ids: Vec<u32>,
}
#[test]
fn streaming_struct_multi_typed_arrays_matches_to_vec() {
let d = SciData {
label: "experiment".into(),
values: vec![1.5, 2.5, 3.5],
flags: vec![true, false, true],
ids: vec![100, 200, 300],
};
let expected = beve::to_vec(&d).unwrap();
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &d).unwrap();
assert_eq!(buf, expected);
}
#[test]
fn streaming_vec_of_structs_is_generic() {
let v = vec![Point { x: 1.0, y: 2.0 }, Point { x: 3.0, y: 4.0 }];
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
let v2: Vec<Point> = beve::from_slice(&buf).unwrap();
assert_eq!(v, v2);
beve::validate_slice(&buf).unwrap();
}
#[test]
fn streaming_nested_vec_vec_f64() {
let v = vec![vec![1.0f64, 2.0], vec![3.0, 4.0, 5.0]];
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &v).unwrap();
let v2: Vec<Vec<f64>> = beve::from_slice(&buf).unwrap();
assert_eq!(v, v2);
let expected = beve::to_vec(&v).unwrap();
assert_eq!(buf, expected);
}
fn streaming_de_round_trip<T>(value: &T) -> T
where
T: Serialize + serde::de::DeserializeOwned + std::fmt::Debug + PartialEq,
{
let bytes = beve::to_vec(value).unwrap();
beve::from_reader_streaming(Cursor::new(bytes)).unwrap()
}
#[test]
fn streaming_de_bool() {
assert!(streaming_de_round_trip(&true));
assert!(!streaming_de_round_trip(&false));
}
#[test]
fn streaming_de_u32() {
assert_eq!(streaming_de_round_trip(&42u32), 42u32);
}
#[test]
fn streaming_de_i64() {
assert_eq!(streaming_de_round_trip(&-100i64), -100i64);
}
#[test]
fn streaming_de_f64() {
assert_eq!(streaming_de_round_trip(&1.5f64), 1.5f64);
}
#[test]
fn streaming_de_string() {
assert_eq!(
streaming_de_round_trip(&"hello world".to_string()),
"hello world"
);
}
#[test]
fn streaming_de_none() {
assert_eq!(streaming_de_round_trip(&None::<u32>), None::<u32>);
}
#[test]
fn streaming_de_some() {
assert_eq!(streaming_de_round_trip(&Some(42u32)), Some(42u32));
}
#[test]
fn streaming_de_unit() {
streaming_de_round_trip(&());
}
#[test]
fn streaming_de_point() {
let p = Point { x: 1.0, y: -2.5 };
assert_eq!(streaming_de_round_trip(&p), p);
}
#[test]
fn streaming_de_scalar_fields() {
let v = ScalarFields {
a: true,
b: 42,
c: -100,
d: 1.5,
e: "hello".into(),
};
assert_eq!(streaming_de_round_trip(&v), v);
}
#[test]
fn streaming_de_nested() {
let n = Nested {
name: "test".into(),
point: Point { x: 0.0, y: 1.0 },
tags: vec!["a".into(), "b".into(), "c".into()],
};
assert_eq!(streaming_de_round_trip(&n), n);
}
#[test]
fn streaming_de_vec_f64() {
let v = vec![1.0f64, 2.0, 3.0, 4.0, 5.0];
assert_eq!(streaming_de_round_trip(&v), v);
}
#[test]
fn streaming_de_vec_u32() {
let v = vec![10u32, 20, 30, 40];
assert_eq!(streaming_de_round_trip(&v), v);
}
#[test]
fn streaming_de_vec_i8() {
let v = vec![-1i8, 0, 1, 127, -128];
assert_eq!(streaming_de_round_trip(&v), v);
}
#[test]
fn streaming_de_vec_bool() {
let v = vec![true, false, true, true, false, false, true, false, true];
assert_eq!(streaming_de_round_trip(&v), v);
}
#[test]
fn streaming_de_vec_string() {
let v = vec!["hello".to_string(), "world".to_string()];
assert_eq!(streaming_de_round_trip(&v), v);
}
#[test]
fn streaming_de_vec_u8() {
let v = vec![1u8, 2, 3, 4, 5];
assert_eq!(streaming_de_round_trip(&v), v);
}
#[test]
fn streaming_de_empty_vec() {
let v: Vec<f64> = vec![];
assert_eq!(streaming_de_round_trip(&v), v);
}
#[test]
fn streaming_de_vec_of_structs() {
let v = vec![Point { x: 1.0, y: 2.0 }, Point { x: 3.0, y: 4.0 }];
assert_eq!(streaming_de_round_trip(&v), v);
}
#[test]
fn streaming_de_hashmap_string_keys() {
let mut m = HashMap::new();
m.insert("x".to_string(), 1.0f64);
m.insert("y".to_string(), 2.0);
assert_eq!(streaming_de_round_trip(&m), m);
}
#[test]
fn streaming_de_u32_key_map() {
let mut m = HashMap::new();
m.insert(1u32, "one".to_string());
m.insert(2u32, "two".to_string());
assert_eq!(streaming_de_round_trip(&m), m);
}
#[test]
fn streaming_de_i64_key_map() {
let mut m = HashMap::new();
m.insert(-1i64, 100u32);
m.insert(42i64, 200u32);
assert_eq!(streaming_de_round_trip(&m), m);
}
#[test]
fn streaming_de_empty_map() {
let m: HashMap<String, u32> = HashMap::new();
assert_eq!(streaming_de_round_trip(&m), m);
}
#[test]
fn streaming_de_unit_variant() {
assert_eq!(streaming_de_round_trip(&Color::Green), Color::Green);
}
#[test]
fn streaming_de_newtype_variant() {
assert_eq!(
streaming_de_round_trip(&Shape::Circle(2.5)),
Shape::Circle(2.5)
);
}
#[test]
fn streaming_de_struct_variant() {
let s = Shape::Rect { w: 3.0, h: 4.0 };
assert_eq!(streaming_de_round_trip(&s), s);
}
#[test]
fn streaming_de_tuple_variant() {
let s = Shape::Triangle(3.0, 4.0, 5.0);
assert_eq!(streaming_de_round_trip(&s), s);
}
#[test]
fn streaming_de_tuple() {
let t = (42u32, "hello".to_string(), true);
assert_eq!(streaming_de_round_trip(&t), t);
}
#[test]
fn streaming_de_optional() {
let v = WithOptional {
a: Some(42),
b: None,
};
assert_eq!(streaming_de_round_trip(&v), v);
}
#[test]
fn streaming_de_large_vec_f64() {
let v: Vec<f64> = (0..10_000).map(|i| i as f64).collect();
assert_eq!(streaming_de_round_trip(&v), v);
}
#[test]
fn streaming_de_large_struct() {
let d = SciData {
label: "experiment".into(),
values: (0..10_000).map(|i| i as f64 * 0.1).collect(),
flags: (0..10_000).map(|i| i % 3 == 0).collect(),
ids: (0..10_000).map(|i| i as u32).collect(),
};
assert_eq!(streaming_de_round_trip(&d), d);
}
#[test]
fn streaming_de_map_of_vecs() {
let mut m = HashMap::new();
m.insert("a".to_string(), vec![1.0f64, 2.0, 3.0]);
m.insert("b".to_string(), vec![4.0, 5.0]);
assert_eq!(streaming_de_round_trip(&m), m);
}
#[test]
fn streaming_de_nested_vec_vec() {
let v = vec![vec![1.0f64, 2.0], vec![3.0, 4.0, 5.0]];
assert_eq!(streaming_de_round_trip(&v), v);
}
#[test]
fn streaming_full_round_trip() {
let d = SciData {
label: "full_streaming".into(),
values: vec![1.0, 2.0, 3.0],
flags: vec![true, false],
ids: vec![100, 200],
};
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &d).unwrap();
let d2: SciData = beve::from_reader_streaming(Cursor::new(buf)).unwrap();
assert_eq!(d, d2);
}
#[test]
fn streaming_complex_float_roundtrip() {
let values = vec![
beve::Complex {
re: 1.0f32,
im: -2.5,
},
beve::Complex { re: 3.0, im: 0.0 },
];
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &values).unwrap();
let back: Vec<beve::Complex<f32>> = beve::from_reader_streaming(Cursor::new(&buf)).unwrap();
assert_eq!(back, values);
}
#[test]
fn streaming_complex_integer_roundtrip() {
let c = beve::Complex {
re: -42i32,
im: 100,
};
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &c).unwrap();
let back: beve::Complex<i32> = beve::from_reader_streaming(Cursor::new(&buf)).unwrap();
assert_eq!(back, c);
let values = vec![
beve::Complex { re: 1i16, im: -2 },
beve::Complex { re: 300, im: -400 },
beve::Complex { re: 0, im: 0 },
];
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &values).unwrap();
let back: Vec<beve::Complex<i16>> = beve::from_reader_streaming(Cursor::new(&buf)).unwrap();
assert_eq!(back, values);
let values = vec![
beve::Complex { re: 10u8, im: 20 },
beve::Complex { re: 255, im: 0 },
];
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &values).unwrap();
let back: Vec<beve::Complex<u8>> = beve::from_reader_streaming(Cursor::new(&buf)).unwrap();
assert_eq!(back, values);
}
#[test]
fn streaming_complex_in_struct_roundtrip() {
#[derive(Serialize, Deserialize, Debug, PartialEq)]
struct Payload {
tag: String,
sample: beve::Complex<i32>,
data: Vec<beve::Complex<u16>>,
}
let p = Payload {
tag: "test".to_string(),
sample: beve::Complex { re: -1, im: 2 },
data: vec![
beve::Complex { re: 100, im: 200 },
beve::Complex { re: 0, im: 65535 },
],
};
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &p).unwrap();
let back: Payload = beve::from_reader_streaming(Cursor::new(&buf)).unwrap();
assert_eq!(back, p);
}
#[test]
fn data_delimiter_constant_is_correct() {
assert_eq!(beve::DATA_DELIMITER, 0x06);
}
#[test]
fn streaming_delimiter_separates_records() {
let r1 = Point { x: 1.0, y: 2.0 };
let r2 = Point { x: 3.0, y: 4.0 };
let r3 = Point { x: 5.0, y: 6.0 };
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &r1).unwrap();
beve::write_delimiter(&mut buf).unwrap();
beve::to_writer_streaming(&mut buf, &r2).unwrap();
beve::write_delimiter(&mut buf).unwrap();
beve::to_writer_streaming(&mut buf, &r3).unwrap();
let mut cursor = Cursor::new(&buf);
let back1: Point = beve::from_reader_streaming(&mut cursor).unwrap();
let back2: Point = beve::from_reader_streaming(&mut cursor).unwrap();
let back3: Point = beve::from_reader_streaming(&mut cursor).unwrap();
assert_eq!(back1, r1);
assert_eq!(back2, r2);
assert_eq!(back3, r3);
}
#[test]
fn streaming_delimiter_with_heterogeneous_types() {
let header = ScalarFields {
a: true,
b: 42,
c: -100,
d: 1.5,
e: "metadata".into(),
};
let batch = vec![1.0f64, 2.0, 3.0];
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &header).unwrap();
beve::write_delimiter(&mut buf).unwrap();
beve::to_writer_streaming(&mut buf, &batch).unwrap();
let mut cursor = Cursor::new(&buf);
let back_header: ScalarFields = beve::from_reader_streaming(&mut cursor).unwrap();
let back_batch: Vec<f64> = beve::from_reader_streaming(&mut cursor).unwrap();
assert_eq!(back_header, header);
assert_eq!(back_batch, batch);
}
#[test]
fn streaming_delimiter_before_enum_value() {
let c1 = Color::Red;
let c2 = Color::Blue;
let s1 = Shape::Rect { w: 3.0, h: 4.0 };
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &c1).unwrap();
beve::write_delimiter(&mut buf).unwrap();
beve::to_writer_streaming(&mut buf, &c2).unwrap();
beve::write_delimiter(&mut buf).unwrap();
beve::to_writer_streaming(&mut buf, &s1).unwrap();
let mut cursor = Cursor::new(&buf);
let back1: Color = beve::from_reader_streaming(&mut cursor).unwrap();
let back2: Color = beve::from_reader_streaming(&mut cursor).unwrap();
let back3: Shape = beve::from_reader_streaming(&mut cursor).unwrap();
assert_eq!(back1, c1);
assert_eq!(back2, c2);
assert_eq!(back3, s1);
}
#[test]
fn slice_delimiter_before_enum_value() {
let c1 = Color::Green;
let c2 = Color::Blue;
let mut buf = Vec::new();
buf.push(beve::DATA_DELIMITER); buf.extend_from_slice(&beve::to_vec(&c1).unwrap());
buf.push(beve::DATA_DELIMITER);
buf.extend_from_slice(&beve::to_vec(&c2).unwrap());
let back1: Color = beve::from_slice(&buf[..]).unwrap();
assert_eq!(back1, c1);
}
#[test]
fn streaming_multiple_consecutive_delimiters() {
let p = Point { x: 1.0, y: 2.0 };
let mut buf = Vec::new();
for _ in 0..5 {
beve::write_delimiter(&mut buf).unwrap();
}
beve::to_writer_streaming(&mut buf, &p).unwrap();
let mut cursor = Cursor::new(&buf);
let back: Point = beve::from_reader_streaming(&mut cursor).unwrap();
assert_eq!(back, p);
}
#[test]
fn streaming_trailing_delimiter_returns_eof() {
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &42u32).unwrap();
beve::write_delimiter(&mut buf).unwrap();
let mut cursor = Cursor::new(&buf);
let _v: u32 = beve::from_reader_streaming(&mut cursor).unwrap();
let result: beve::Result<u32> = beve::from_reader_streaming(&mut cursor);
assert!(result.is_err());
}
#[test]
fn streaming_delimiter_before_scalars() {
let mut buf = Vec::new();
beve::to_writer_streaming(&mut buf, &42u32).unwrap();
beve::write_delimiter(&mut buf).unwrap();
beve::to_writer_streaming(&mut buf, &2.78f64).unwrap();
beve::write_delimiter(&mut buf).unwrap();
beve::to_writer_streaming(&mut buf, &true).unwrap();
beve::write_delimiter(&mut buf).unwrap();
beve::to_writer_streaming(&mut buf, &"hello").unwrap();
beve::write_delimiter(&mut buf).unwrap();
beve::to_writer_streaming(&mut buf, &vec![1u8, 2, 3]).unwrap();
let mut cursor = Cursor::new(&buf);
let v1: u32 = beve::from_reader_streaming(&mut cursor).unwrap();
let v2: f64 = beve::from_reader_streaming(&mut cursor).unwrap();
let v3: bool = beve::from_reader_streaming(&mut cursor).unwrap();
let v4: String = beve::from_reader_streaming(&mut cursor).unwrap();
let v5: Vec<u8> = beve::from_reader_streaming(&mut cursor).unwrap();
assert_eq!(v1, 42);
assert_eq!(v2, 2.78);
assert!(v3);
assert_eq!(v4, "hello");
assert_eq!(v5, vec![1, 2, 3]);
}
#[test]
fn slice_multiple_consecutive_delimiters() {
let mut buf = vec![beve::DATA_DELIMITER; 3];
buf.extend_from_slice(&beve::to_vec(&99i64).unwrap());
let v: i64 = beve::from_slice(&buf).unwrap();
assert_eq!(v, 99);
}
#[test]
fn streaming_de_truncated_input() {
let bytes = beve::to_vec(&42u32).unwrap();
let result: beve::Result<u32> = beve::from_reader_streaming(Cursor::new(&bytes[..1]));
assert!(result.is_err());
}
#[test]
fn streaming_de_empty_input() {
let result: beve::Result<u32> = beve::from_reader_streaming(Cursor::new(&[]));
assert!(result.is_err());
}