pub mod de; pub mod ser; pub mod symbol; pub mod value; #[cfg(test)] mod dom { use super::value::{Value, PlainValue, NestedValue, Domain, Encoder, Codec, writer::Writer}; #[derive(Debug, Hash, Clone, Ord, PartialEq, Eq, PartialOrd)] pub enum Dom { One, Two, } impl Domain for Dom { fn encode<'a, 'b, W: Writer, N: NestedValue>( &self, enc: &mut Encoder<'a, 'b, W, N, Self>) -> super::value::encoder::Result { match self { Dom::One => { enc.write.stream_bytes()?; enc.write.write_bytes(&[255, 255, 255, 255])?; enc.write.close_stream() } Dom::Two => enc.write(&self.as_preserves()?) } } fn as_preserves>(&self) -> Result { Ok(Value::symbol(&format!("Dom::{:?}", self)).wrap()) } } #[test] fn test_one() { let v: PlainValue<_> = Value::from(vec![Value::from(1).wrap(), Value::Domain(Dom::One).wrap(), Value::from(2).wrap()]) .wrap(); assert_eq!(Codec::without_placeholders().encode_bytes(&v).unwrap(), [147, 49, 38, 100, 255, 255, 255, 255, 4, 50]); } #[test] fn test_two() { let v: PlainValue<_> = Value::from(vec![Value::from(1).wrap(), Value::Domain(Dom::Two).wrap(), Value::from(2).wrap()]) .wrap(); assert_eq!(Codec::without_placeholders().encode_bytes(&v).unwrap(), [147, 49, 120, 68, 111, 109, 58, 58, 84, 119, 111, 50]); } } #[cfg(test)] mod ieee754_section_5_10_total_order_tests { use std::cmp::Ordering::{Less, Equal, Greater}; use super::dom::Dom; use crate::value::{Value, PlainValue}; fn f(val: f32) -> Value, Dom> { Value::from(val) } fn d(val: f64) -> Value, Dom> { Value::from(val) } // TODO: Test cases with a few different signalling and non-signalling NaNs #[test] fn case32_a_1() { assert_eq!(f(1.0).cmp(&f(2.0)), Less) } #[test] fn case32_a_2() { assert_eq!(f(-1.0).cmp(&f(1.0)), Less) } #[test] fn case32_a_3() { assert_eq!(f(0.0).cmp(&f(1.0)), Less) } #[test] fn case32_a_4() { assert_eq!(f(-1.0).cmp(&f(0.0)), Less) } #[test] fn case32_a_5() { assert_eq!(f(-1e32).cmp(&f(-1e31)), Less) } #[test] fn case32_a_6() { assert_eq!(f(-1e32).cmp(&f(1e33)), Less) } #[test] fn case32_a_7() { assert_eq!(f(std::f32::NEG_INFINITY).cmp(&f(std::f32::INFINITY)), Less) } #[test] fn case32_a_8() { assert_eq!(f(std::f32::NEG_INFINITY).cmp(&f(0.0)), Less) } #[test] fn case32_a_9() { assert_eq!(f(std::f32::NEG_INFINITY).cmp(&f(1.0)), Less) } #[test] fn case32_a_10() { assert_eq!(f(std::f32::NEG_INFINITY).cmp(&f(1e33)), Less) } #[test] fn case32_a_11() { assert_eq!(f(0.0).cmp(&f(std::f32::INFINITY)), Less) } #[test] fn case32_a_12() { assert_eq!(f(1.0).cmp(&f(std::f32::INFINITY)), Less) } #[test] fn case32_a_13() { assert_eq!(f(1e33).cmp(&f(std::f32::INFINITY)), Less) } #[test] fn case32_b_1() { assert_eq!(f(2.0).cmp(&f(1.0)), Greater) } #[test] fn case32_b_2() { assert_eq!(f(1.0).cmp(&f(-1.0)), Greater) } #[test] fn case32_b_3() { assert_eq!(f(1.0).cmp(&f(0.0)), Greater) } #[test] fn case32_b_4() { assert_eq!(f(0.0).cmp(&f(-1.0)), Greater) } #[test] fn case32_b_5() { assert_eq!(f(-1e31).cmp(&f(-1e32)), Greater) } #[test] fn case32_b_6() { assert_eq!(f(1e33).cmp(&f(-1e32)), Greater) } #[test] fn case32_b_7() { assert_eq!(f(std::f32::INFINITY).cmp(&f(std::f32::NEG_INFINITY)), Greater) } #[test] fn case32_b_8() { assert_eq!(f(std::f32::INFINITY).cmp(&f(0.0)), Greater) } #[test] fn case32_b_9() { assert_eq!(f(std::f32::INFINITY).cmp(&f(1.0)), Greater) } #[test] fn case32_b_10() { assert_eq!(f(std::f32::INFINITY).cmp(&f(1e33)), Greater) } #[test] fn case32_b_11() { assert_eq!(f(0.0).cmp(&f(std::f32::NEG_INFINITY)), Greater) } #[test] fn case32_b_12() { assert_eq!(f(1.0).cmp(&f(std::f32::NEG_INFINITY)), Greater) } #[test] fn case32_b_13() { assert_eq!(f(1e33).cmp(&f(std::f32::NEG_INFINITY)), Greater) } #[test] fn case32_c1() { assert_eq!(f(-0.0).cmp(&f( 0.0)), Less) } #[test] fn case32_c2() { assert_eq!(f( 0.0).cmp(&f(-0.0)), Greater) } #[test] fn case32_c3_1() { assert_eq!(f(-0.0).cmp(&f(-0.0)), Equal) } #[test] fn case32_c3_2() { assert_eq!(f( 0.0).cmp(&f( 0.0)), Equal) } #[test] fn case32_c3_3() { assert_eq!(f(1.0).cmp(&f(1.0)), Equal) } #[test] fn case32_c3_4() { assert_eq!(f(-1.0).cmp(&f(-1.0)), Equal) } #[test] fn case32_c3_5() { assert_eq!(f(-1e32).cmp(&f(-1e32)), Equal) } #[test] fn case32_c3_6() { assert_eq!(f(1e33).cmp(&f(1e33)), Equal) } #[test] fn case64_a_1() { assert_eq!(d(1.0).cmp(&d(2.0)), Less) } #[test] fn case64_a_2() { assert_eq!(d(-1.0).cmp(&d(1.0)), Less) } #[test] fn case64_a_3() { assert_eq!(d(0.0).cmp(&d(1.0)), Less) } #[test] fn case64_a_4() { assert_eq!(d(-1.0).cmp(&d(0.0)), Less) } #[test] fn case64_a_5() { assert_eq!(d(-1e32).cmp(&d(-1e31)), Less) } #[test] fn case64_a_6() { assert_eq!(d(-1e32).cmp(&d(1e33)), Less) } #[test] fn case64_a_7() { assert_eq!(d(std::f64::NEG_INFINITY).cmp(&d(std::f64::INFINITY)), Less) } #[test] fn case64_a_8() { assert_eq!(d(std::f64::NEG_INFINITY).cmp(&d(0.0)), Less) } #[test] fn case64_a_9() { assert_eq!(d(std::f64::NEG_INFINITY).cmp(&d(1.0)), Less) } #[test] fn case64_a_10() { assert_eq!(d(std::f64::NEG_INFINITY).cmp(&d(1e33)), Less) } #[test] fn case64_a_11() { assert_eq!(d(0.0).cmp(&d(std::f64::INFINITY)), Less) } #[test] fn case64_a_12() { assert_eq!(d(1.0).cmp(&d(std::f64::INFINITY)), Less) } #[test] fn case64_a_13() { assert_eq!(d(1e33).cmp(&d(std::f64::INFINITY)), Less) } #[test] fn case64_b_1() { assert_eq!(d(2.0).cmp(&d(1.0)), Greater) } #[test] fn case64_b_2() { assert_eq!(d(1.0).cmp(&d(-1.0)), Greater) } #[test] fn case64_b_3() { assert_eq!(d(1.0).cmp(&d(0.0)), Greater) } #[test] fn case64_b_4() { assert_eq!(d(0.0).cmp(&d(-1.0)), Greater) } #[test] fn case64_b_5() { assert_eq!(d(-1e31).cmp(&d(-1e32)), Greater) } #[test] fn case64_b_6() { assert_eq!(d(1e33).cmp(&d(-1e32)), Greater) } #[test] fn case64_b_7() { assert_eq!(d(std::f64::INFINITY).cmp(&d(std::f64::NEG_INFINITY)), Greater) } #[test] fn case64_b_8() { assert_eq!(d(std::f64::INFINITY).cmp(&d(0.0)), Greater) } #[test] fn case64_b_9() { assert_eq!(d(std::f64::INFINITY).cmp(&d(1.0)), Greater) } #[test] fn case64_b_10() { assert_eq!(d(std::f64::INFINITY).cmp(&d(1e33)), Greater) } #[test] fn case64_b_11() { assert_eq!(d(0.0).cmp(&d(std::f64::NEG_INFINITY)), Greater) } #[test] fn case64_b_12() { assert_eq!(d(1.0).cmp(&d(std::f64::NEG_INFINITY)), Greater) } #[test] fn case64_b_13() { assert_eq!(d(1e33).cmp(&d(std::f64::NEG_INFINITY)), Greater) } #[test] fn case64_c1() { assert_eq!(d(-0.0).cmp(&d( 0.0)), Less) } #[test] fn case64_c2() { assert_eq!(d( 0.0).cmp(&d(-0.0)), Greater) } #[test] fn case64_c3_1() { assert_eq!(d(-0.0).cmp(&d(-0.0)), Equal) } #[test] fn case64_c3_2() { assert_eq!(d( 0.0).cmp(&d( 0.0)), Equal) } #[test] fn case64_c3_3() { assert_eq!(d(1.0).cmp(&d(1.0)), Equal) } #[test] fn case64_c3_4() { assert_eq!(d(-1.0).cmp(&d(-1.0)), Equal) } #[test] fn case64_c3_5() { assert_eq!(d(-1e32).cmp(&d(-1e32)), Equal) } #[test] fn case64_c3_6() { assert_eq!(d(1e33).cmp(&d(1e33)), Equal) } } #[cfg(test)] mod value_tests { use crate::value::{Value, PlainValue}; use num::bigint::BigInt; use super::dom::Dom; type VV = Value, Dom>; #[test] fn boolean_mut() { let mut b = VV::Boolean(true); assert!(b.is_boolean()); *(b.as_boolean_mut().unwrap()) = false; assert_eq!(b, VV::Boolean(false)); } #[test] fn float_mut() { let mut f = VV::from(1.0f32); assert!(f.is_float()); *(f.as_float_mut().unwrap()) = 123.45; assert_eq!(f, VV::from(123.45f32)); assert_eq!(f.as_float().unwrap(), 123.45f32); } #[test] fn double_mut() { let mut f = VV::from(1.0); assert!(f.is_double()); *(f.as_double_mut().unwrap()) = 123.45; assert_eq!(f, VV::from(123.45)); assert_eq!(f.as_double().unwrap(), 123.45); } #[test] fn signedinteger_mut() { let mut i = VV::from(123); assert!(i.is_signedinteger()); *(i.as_signedinteger_mut().unwrap()) = BigInt::from(234); assert_eq!(i, VV::from(234)); use num::traits::cast::ToPrimitive; assert_eq!(i.as_signedinteger().unwrap().to_i64().unwrap(), 234); } #[test] fn string_mut() { let mut s = VV::from("hello, world!"); assert!(s.is_string()); s.as_string_mut().unwrap().replace_range(7..12, "there"); assert_eq!(s, VV::from("hello, there!")); } #[test] fn bytes_mut() { let mut b = VV::from(&b"hello, world!"[..]); assert!(b.is_bytestring()); b.as_bytestring_mut().unwrap().splice(7..12, Vec::from(&b"there"[..])); assert_eq!(b, VV::from(&b"hello, there!"[..])); } #[test] fn symbol_mut() { let mut s = VV::symbol("abcd"); assert!(s.is_symbol()); s.as_symbol_mut().unwrap().replace_range(..2, "AB"); assert_eq!(s, VV::symbol("ABcd")); } #[test] fn record_mut() { let says = VV::symbol("says").wrap(); let mut r = VV::record(says.clone(), vec![VV::from("Tony").wrap(), VV::from("Hello!").wrap()]); assert_eq!(r.as_record_mut(Some(0)), None); assert_eq!(r.as_record_mut(Some(1)), None); assert!(r.as_record_mut(Some(2)).is_some()); assert_eq!(r.as_record_mut(Some(3)), None); r.as_record_mut(None).unwrap().1[0] = VV::from("Alice").wrap(); assert_eq!(r, VV::record(says, vec![VV::from("Alice").wrap(), VV::from("Hello!").wrap()])); } #[test] fn sequence_mut() { let mut s = VV::Sequence(vec![VV::from(1).wrap(), VV::from(2).wrap(), VV::from(3).wrap()]); let r = VV::Sequence(vec![VV::from(1).wrap(), VV::from(99).wrap(), VV::from(3).wrap()]); s.as_sequence_mut().unwrap()[1] = VV::from(99).wrap(); assert_eq!(r, s); } } #[cfg(test)] mod decoder_tests { use crate::value::{Decoder, BinaryReader, Reader}; use crate::value::{Value, PlainValue, NestedValue}; use super::dom::Dom; #[test] fn skip_annotations_noskip() { let mut buf = &b"\x0521"[..]; let r = BinaryReader::new(&mut buf); let mut d = Decoder::<_, PlainValue, Dom>::new(r, None); let v = d.next_or_err().unwrap(); assert_eq!(v.annotations().len(), 1); assert_eq!(v.annotations()[0], Value::from(2).wrap()); assert_eq!(v.value(), &Value::from(1)); } #[test] fn skip_annotations_skip() { let mut buf = &b"\x0521"[..]; let r = BinaryReader::new(&mut buf); let mut d = Decoder::<_, PlainValue, Dom>::new(r, None); d.set_read_annotations(false); let v = d.next_or_err().unwrap(); assert_eq!(v.annotations().len(), 0); assert_eq!(v.value(), &Value::from(1)); } #[test] fn two_values_at_once() { let mut buf = &b"\x81tPing\x81tPong"[..]; assert_eq!(buf.len(), 12); let r = BinaryReader::new(&mut buf); let mut d = Decoder::<_, PlainValue, Dom>::new(r, None); assert_eq!(d.next_or_err().unwrap().value(), &Value::simple_record("Ping", vec![])); assert_eq!(d.next_or_err().unwrap().value(), &Value::simple_record("Pong", vec![])); assert_eq!(buf.len(), 0); } #[test] fn buf_advanced() { let mut buf = &b"\x81tPing\x81tPong"[..]; assert_eq!(buf.len(), 12); let mut r = BinaryReader::new(&mut buf); let mut d = Decoder::<_, PlainValue, Dom>::new(&mut r, None); assert_eq!(d.next_or_err().unwrap().value(), &Value::simple_record("Ping", vec![])); assert!(r.buffered_len().unwrap() > 0); let mut d = Decoder::<_, PlainValue, Dom>::new(&mut r, None); assert_eq!(d.next_or_err().unwrap().value(), &Value::simple_record("Pong", vec![])); assert!(r.buffered_len().unwrap() == 0); assert_eq!(buf.len(), 0); } } #[cfg(test)] mod samples_tests { use crate::symbol::Symbol; use crate::value::{Codec, Decoder, BinaryReader}; use crate::value::reader::is_syntax_error; use crate::value::{Value, PlainValue, Map}; use crate::value::DecodePlaceholderMap; use crate::value::to_value; use crate::value::from_value; use super::dom::Dom; #[derive(Debug, serde::Serialize, serde::Deserialize)] struct ExpectedPlaceholderMapping(DecodePlaceholderMap, Dom>); #[derive(Debug, serde::Serialize, serde::Deserialize)] struct TestCases { decode_placeholders: ExpectedPlaceholderMapping, tests: Map } #[derive(Debug, serde::Serialize, serde::Deserialize)] enum TestCase { Test(#[serde(with = "serde_bytes")] Vec, PlainValue), NondeterministicTest(#[serde(with = "serde_bytes")] Vec, PlainValue), StreamingTest(#[serde(with = "serde_bytes")] Vec, PlainValue), DecodeTest(#[serde(with = "serde_bytes")] Vec, PlainValue), ParseError(String), ParseShort(String), DecodeError(#[serde(with = "serde_bytes")] Vec), DecodeShort(#[serde(with = "serde_bytes")] Vec), } #[test] fn run() -> std::io::Result<()> { let mut fh = std::fs::File::open("../../tests/samples.bin").unwrap(); let r = BinaryReader::new(&mut fh); let mut d = Decoder::<_, PlainValue, Dom>::new(r, None); let tests: TestCases = from_value(&d.next_or_err().unwrap()).unwrap(); // println!("{:#?}", tests); let codec = Codec::new(tests.decode_placeholders.0); for (Symbol(ref name), ref case) in tests.tests { println!("{:?} ==> {:?}", name, case); match case { TestCase::Test(ref bin, ref val) => { assert_eq!(&codec.decode_all(&mut &codec.encode_bytes(val)?[..])?, &[val.clone()]); assert_eq!(&codec.decode_all(&mut &bin[..])?, &[val.clone()]); assert_eq!(&codec.encode_bytes(val)?, bin); } TestCase::NondeterministicTest(ref bin, ref val) => { // The test cases in samples.txt are carefully // written so that while strictly // "nondeterministic", the order of keys in // dictionaries follows Preserves order. assert_eq!(&codec.decode_all(&mut &codec.encode_bytes(val)?[..])?, &[val.clone()]); assert_eq!(&codec.decode_all(&mut &bin[..])?, &[val.clone()]); assert_eq!(&codec.encode_bytes(val)?, bin); } TestCase::StreamingTest(ref bin, ref val) => { assert_eq!(&codec.decode_all(&mut &codec.encode_bytes(val)?[..])?, &[val.clone()]); assert_eq!(&codec.decode_all(&mut &bin[..])?, &[val.clone()]); } TestCase::DecodeTest(ref bin, ref val) => { assert_eq!(&codec.decode_all(&mut &codec.encode_bytes(val)?[..])?, &[val.clone()]); assert_eq!(&codec.decode_all(&mut &bin[..])?, &[val.clone()]); } TestCase::ParseError(_) => (), TestCase::ParseShort(_) => (), TestCase::DecodeError(ref bin) => { match codec.decode_all(&mut &bin[..]) { Ok(_) => panic!("Unexpected success"), Err(e) => if is_syntax_error(&e) { () } else { panic!("Unexpected error {:?}", e) } } } TestCase::DecodeShort(ref bin) => { assert_eq!(codec.decode_all(&mut &bin[..])?.len(), 0); } } } Ok(()) } #[test] fn simple_to_value() { use serde::Serialize; #[derive(Debug, PartialEq, Eq, serde::Serialize, serde::Deserialize)] struct SimpleValue<'a>(String, #[serde(with = "crate::symbol")] String, Symbol, #[serde(with = "crate::symbol")] String, Symbol, &'a str, #[serde(with = "serde_bytes")] &'a [u8], #[serde(with = "serde_bytes")] Vec, i16, PlainValue); let v = SimpleValue("hello".to_string(), "sym1".to_string(), Symbol("sym2".to_string()), "sym3".to_string(), Symbol("sym4".to_string()), "world", &b"slice"[..], b"vec".to_vec(), 12345, Value::from("hi").wrap()); println!("== v: {:#?}", v); let w: PlainValue = to_value(&v).unwrap(); println!("== w: {:#?}", w); let x = from_value(&w).unwrap(); println!("== x: {:#?}", &x); assert_eq!(v, x); let mut placeholders = Map::new(); placeholders.insert(5, Value::symbol("sym1")); placeholders.insert(500, Value::symbol("sym2")); placeholders.insert(0, Value::symbol("SimpleValue")); let v_bytes_1 = Codec::new(placeholders.clone()).encode_bytes(&w).unwrap(); let mut v_bytes_2 = Vec::new(); v.serialize(&mut crate::ser::Serializer::new(&mut v_bytes_2, Some(&crate::value::invert_map(&placeholders)))).unwrap(); println!("== w bytes = {:?}", v_bytes_1); println!("== v bytes = {:?}", v_bytes_2); assert_eq!(v_bytes_1, v_bytes_2); } }