diff --git a/src/error.rs b/src/error.rs new file mode 100644 index 0000000..3e99f8a --- /dev/null +++ b/src/error.rs @@ -0,0 +1,22 @@ +use std::fmt; + +/// An error that occurs during parsing or serialization. +#[derive(Debug)] +#[cfg_attr(test, derive(PartialEq))] +pub struct Error { + msg: &'static str, +} + +impl Error { + pub(crate) fn new(msg: &'static str) -> Self { + Self { msg } + } +} + +impl fmt::Display for Error { + fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { + f.write_str(self.msg) + } +} + +impl std::error::Error for Error {} diff --git a/src/lib.rs b/src/lib.rs index 7806098..9502e86 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -164,6 +164,7 @@ assert_eq!( ``` */ +mod error; mod parser; mod ref_serializer; mod serializer; @@ -180,11 +181,12 @@ pub use rust_decimal::{ Decimal, }; +pub use error::Error; pub use parser::{ParseMore, Parser}; pub use ref_serializer::{RefDictSerializer, RefItemSerializer, RefListSerializer}; pub use serializer::SerializeValue; -type SFVResult = std::result::Result; +type SFVResult = std::result::Result; /// Represents `Item` type structured field value. /// Can be used as a member of `List` or `Dictionary`. diff --git a/src/parser.rs b/src/parser.rs index 9ec3b72..ff695b3 100644 --- a/src/parser.rs +++ b/src/parser.rs @@ -1,6 +1,7 @@ use crate::utils; use crate::{ - BareItem, Decimal, Dictionary, InnerList, Item, List, ListEntry, Num, Parameters, SFVResult, + BareItem, Decimal, Dictionary, Error, InnerList, Item, List, ListEntry, Num, Parameters, + SFVResult, }; trait ParseValue { @@ -55,14 +56,16 @@ impl ParseValue for List { if let Some(c) = parser.input.next() { if c != b',' { - return Err("parse_list: trailing characters after list member"); + return Err(Error::new( + "parse_list: trailing characters after list member", + )); } } parser.consume_ows_chars(); if parser.input.peek().is_none() { - return Err("parse_list: trailing comma"); + return Err(Error::new("parse_list: trailing comma")); } } @@ -99,14 +102,16 @@ impl ParseValue for Dictionary { if let Some(c) = parser.input.next() { if c != b',' { - return Err("parse_dict: trailing characters after dictionary member"); + return Err(Error::new( + "parse_dict: trailing characters after dictionary member", + )); } } parser.consume_ows_chars(); if parser.input.peek().is_none() { - return Err("parse_dict: trailing comma"); + return Err(Error::new("parse_dict: trailing comma")); } } Ok(dict) @@ -172,7 +177,7 @@ impl<'a> Parser<'a> { self.consume_sp_chars(); if self.input.peek().is_some() { - return Err("parse: trailing characters after parsed value"); + return Err(Error::new("parse: trailing characters after parsed value")); }; Ok(output) } @@ -197,7 +202,9 @@ impl<'a> Parser<'a> { // https://httpwg.org/specs/rfc8941.html#parse-innerlist if Some(b'(') != self.input.next() { - return Err("parse_inner_list: input does not start with '('"); + return Err(Error::new( + "parse_inner_list: input does not start with '('", + )); } let mut inner_list = Vec::new(); @@ -218,18 +225,20 @@ impl<'a> Parser<'a> { if let Some(c) = self.input.peek() { if c != &b' ' && c != &b')' { - return Err("parse_inner_list: bad delimitation"); + return Err(Error::new("parse_inner_list: bad delimitation")); } } } - Err("parse_inner_list: the end of the inner list was not found") + Err(Error::new( + "parse_inner_list: the end of the inner list was not found", + )) } pub(crate) fn parse_bare_item(&mut self) -> SFVResult { // https://httpwg.org/specs/rfc8941.html#parse-bare-item if self.input.peek().is_none() { - return Err("parse_bare_item: empty item"); + return Err(Error::new("parse_bare_item: empty item")); } match self.input.peek() { @@ -243,7 +252,7 @@ impl<'a> Parser<'a> { Num::Decimal(val) => Ok(BareItem::Decimal(val)), Num::Integer(val) => Ok(BareItem::Integer(val)), }, - _ => Err("parse_bare_item: item type can't be identified"), + _ => Err(Error::new("parse_bare_item: item type can't be identified")), } } @@ -251,13 +260,13 @@ impl<'a> Parser<'a> { // https://httpwg.org/specs/rfc8941.html#parse-boolean if self.input.next() != Some(b'?') { - return Err("parse_bool: first character is not '?'"); + return Err(Error::new("parse_bool: first character is not '?'")); } match self.input.next() { Some(b'0') => Ok(false), Some(b'1') => Ok(true), - _ => Err("parse_bool: invalid variant"), + _ => Err(Error::new("parse_bool: invalid variant")), } } @@ -265,25 +274,27 @@ impl<'a> Parser<'a> { // https://httpwg.org/specs/rfc8941.html#parse-string if self.input.next() != Some(b'"') { - return Err("parse_string: first character is not '\"'"); + return Err(Error::new("parse_string: first character is not '\"'")); } let mut output_string = String::from(""); while let Some(curr_char) = self.input.next() { match curr_char { b'"' => return Ok(output_string), - 0x00..=0x1f | 0x7f..=0xff => return Err("parse_string: invalid string character"), + 0x00..=0x1f | 0x7f..=0xff => { + return Err(Error::new("parse_string: invalid string character")) + } b'\\' => match self.input.next() { Some(c @ b'\\' | c @ b'\"') => { output_string.push(c as char); } - None => return Err("parse_string: last input character is '\\'"), - _ => return Err("parse_string: disallowed character after '\\'"), + None => return Err(Error::new("parse_string: last input character is '\\'")), + _ => return Err(Error::new("parse_string: disallowed character after '\\'")), }, _ => output_string.push(curr_char as char), } } - Err("parse_string: no closing '\"'") + Err(Error::new("parse_string: no closing '\"'")) } pub(crate) fn parse_token(&mut self) -> SFVResult { @@ -291,10 +302,12 @@ impl<'a> Parser<'a> { if let Some(first_char) = self.input.peek() { if !first_char.is_ascii_alphabetic() && first_char != &b'*' { - return Err("parse_token: first character is not ALPHA or '*'"); + return Err(Error::new( + "parse_token: first character is not ALPHA or '*'", + )); } } else { - return Err("parse_token: empty input string"); + return Err(Error::new("parse_token: empty input string")); } let mut output_string = String::from(""); @@ -305,7 +318,7 @@ impl<'a> Parser<'a> { match self.input.next() { Some(c) => output_string.push(c as char), - None => return Err("parse_token: end of the string"), + None => return Err(Error::new("parse_token: end of the string")), } } Ok(output_string) @@ -315,7 +328,7 @@ impl<'a> Parser<'a> { // https://httpwg.org/specs/rfc8941.html#parse-binary if self.input.next() != Some(b':') { - return Err("parse_byte_seq: first char is not ':'"); + return Err(Error::new("parse_byte_seq: first char is not ':'")); } let mut b64_content = vec![]; @@ -323,13 +336,13 @@ impl<'a> Parser<'a> { match self.input.next() { Some(b':') => break, Some(c) => b64_content.push(c), - None => return Err("parse_byte_seq: no closing ':'"), + None => return Err(Error::new("parse_byte_seq: no closing ':'")), } } match base64::Engine::decode(&utils::BASE64, b64_content) { Ok(content) => Ok(content), - Err(_) => Err("parse_byte_seq: decoding error"), + Err(_) => Err(Error::new("parse_byte_seq: decoding error")), } } @@ -352,7 +365,7 @@ impl<'a> Parser<'a> { self.input.next(); char_to_i64(c) } - _ => return Err("parse_number: expected digit"), + _ => return Err(Error::new("parse_number: expected digit")), }; let mut digits = 1; @@ -361,7 +374,9 @@ impl<'a> Parser<'a> { match self.input.peek() { Some(b'.') => { if digits > 12 { - return Err("parse_number: too many digits before decimal point"); + return Err(Error::new( + "parse_number: too many digits before decimal point", + )); } self.input.next(); break; @@ -369,7 +384,7 @@ impl<'a> Parser<'a> { Some(&c @ b'0'..=b'9') => { digits += 1; if digits > 15 { - return Err("parse_number: too many digits"); + return Err(Error::new("parse_number: too many digits")); } self.input.next(); magnitude = magnitude * 10 + char_to_i64(c); @@ -382,7 +397,9 @@ impl<'a> Parser<'a> { while let Some(&c @ b'0'..=b'9') = self.input.peek() { if digits == 3 { - return Err("parse_number: too many digits after decimal point"); + return Err(Error::new( + "parse_number: too many digits after decimal point", + )); } self.input.next(); @@ -391,7 +408,7 @@ impl<'a> Parser<'a> { } if digits == 0 { - Err("parse_number: trailing decimal point") + Err(Error::new("parse_number: trailing decimal point")) } else { Ok(Num::Decimal(Decimal::from_i128_with_scale( (sign * magnitude) as i128, @@ -433,7 +450,11 @@ impl<'a> Parser<'a> { pub(crate) fn parse_key(&mut self) -> SFVResult { match self.input.peek() { Some(c) if c == &b'*' || c.is_ascii_lowercase() => (), - _ => return Err("parse_key: first character is not lcalpha or '*'"), + _ => { + return Err(Error::new( + "parse_key: first character is not lcalpha or '*'", + )) + } } let mut output = String::new(); diff --git a/src/ref_serializer.rs b/src/ref_serializer.rs index 7d19c77..8e7a784 100644 --- a/src/ref_serializer.rs +++ b/src/ref_serializer.rs @@ -1,5 +1,5 @@ use crate::serializer::Serializer; -use crate::{AsRefBareItem, RefBareItem, SFVResult}; +use crate::{AsRefBareItem, Error, RefBareItem, SFVResult}; use std::marker::PhantomData; /// Serializes `Item` field value components incrementally. @@ -94,7 +94,9 @@ impl<'a> RefListSerializer<'a> { pub fn parameter(self, name: &str, value: impl AsRefBareItem) -> SFVResult { if self.buffer.is_empty() { - return Err("parameters must be serialized after bare item or inner list"); + return Err(Error::new( + "parameters must be serialized after bare item or inner list", + )); } Serializer::serialize_parameter(name, value, self.buffer)?; Ok(RefListSerializer { @@ -170,7 +172,9 @@ impl<'a> RefDictSerializer<'a> { pub fn parameter(self, name: &str, value: impl AsRefBareItem) -> SFVResult { if self.buffer.is_empty() { - return Err("parameters must be serialized after bare item or inner list"); + return Err(Error::new( + "parameters must be serialized after bare item or inner list", + )); } Serializer::serialize_parameter(name, value, self.buffer)?; Ok(RefDictSerializer { @@ -212,7 +216,9 @@ impl<'a, T: Container<'a>> RefInnerListSerializer<'a, T> { pub fn inner_list_parameter(self, name: &str, value: impl AsRefBareItem) -> SFVResult { if self.buffer.is_empty() { - return Err("parameters must be serialized after bare item or inner list"); + return Err(Error::new( + "parameters must be serialized after bare item or inner list", + )); } Serializer::serialize_parameter(name, value, self.buffer)?; Ok(RefInnerListSerializer { diff --git a/src/serializer.rs b/src/serializer.rs index b45d469..6ba26e3 100644 --- a/src/serializer.rs +++ b/src/serializer.rs @@ -1,7 +1,7 @@ use crate::utils; use crate::{ - AsRefBareItem, BareItem, Decimal, Dictionary, InnerList, Item, List, ListEntry, Parameters, - RefBareItem, SFVResult, + AsRefBareItem, BareItem, Decimal, Dictionary, Error, InnerList, Item, List, ListEntry, + Parameters, RefBareItem, SFVResult, }; use std::fmt::Write as _; @@ -63,7 +63,9 @@ impl Serializer { pub(crate) fn serialize_list(input_list: &List, output: &mut String) -> SFVResult<()> { // https://httpwg.org/specs/rfc8941.html#ser-list if input_list.is_empty() { - return Err("serialize_list: serializing empty field is not allowed"); + return Err(Error::new( + "serialize_list: serializing empty field is not allowed", + )); } for (idx, member) in input_list.iter().enumerate() { @@ -89,7 +91,9 @@ impl Serializer { pub(crate) fn serialize_dict(input_dict: &Dictionary, output: &mut String) -> SFVResult<()> { // https://httpwg.org/specs/rfc8941.html#ser-dictionary if input_dict.is_empty() { - return Err("serialize_dictionary: serializing empty field is not allowed"); + return Err(Error::new( + "serialize_dictionary: serializing empty field is not allowed", + )); } for (idx, (member_name, member_value)) in input_dict.iter().enumerate() { @@ -191,10 +195,12 @@ impl Serializer { // https://httpwg.org/specs/rfc8941.html#ser-key match input_key.chars().next() { - None => return Err("serialize_key: key is empty"), + None => return Err(Error::new("serialize_key: key is empty")), Some(char) => { if !(char.is_ascii_lowercase() || char == '*') { - return Err("serialize_key: first character is not lcalpha or '*'"); + return Err(Error::new( + "serialize_key: first character is not lcalpha or '*'", + )); } } } @@ -203,7 +209,7 @@ impl Serializer { |c: char| !(c.is_ascii_lowercase() || c.is_ascii_digit() || "_-*.".contains(c)); if input_key.chars().any(disallowed_chars) { - return Err("serialize_key: disallowed character in input"); + return Err(Error::new("serialize_key: disallowed character in input")); } output.push_str(input_key); @@ -215,7 +221,7 @@ impl Serializer { let (min_int, max_int) = (-999_999_999_999_999_i64, 999_999_999_999_999_i64); if !(min_int <= value && value <= max_int) { - return Err("serialize_integer: integer is out of range"); + return Err(Error::new("serialize_integer: integer is out of range")); } write!(output, "{}", value).unwrap(); Ok(()) @@ -231,7 +237,9 @@ impl Serializer { let fract_comp = decimal.fract(); if int_comp.abs() > Decimal::from(999_999_999_999_i64) { - return Err("serialize_decimal: integer component > 12 digits"); + return Err(Error::new( + "serialize_decimal: integer component > 12 digits", + )); } if fract_comp.is_zero() { @@ -247,12 +255,12 @@ impl Serializer { // https://httpwg.org/specs/rfc8941.html#ser-integer if !value.is_ascii() { - return Err("serialize_string: non-ascii character"); + return Err(Error::new("serialize_string: non-ascii character")); } let vchar_or_sp = |char| char == '\x7f' || ('\x00'..='\x1f').contains(&char); if value.chars().any(vchar_or_sp) { - return Err("serialize_string: not a visible character"); + return Err(Error::new("serialize_string: not a visible character")); } output.push('\"'); @@ -271,14 +279,16 @@ impl Serializer { // https://httpwg.org/specs/rfc8941.html#ser-token if !value.is_ascii() { - return Err("serialize_token: non-ascii character"); + return Err(Error::new("serialize_token: non-ascii character")); } match value.chars().next() { - None => return Err("serialize_token: token is empty"), + None => return Err(Error::new("serialize_token: token is empty")), Some(char) => { if !(char.is_ascii_alphabetic() || char == '*') { - return Err("serialize_token: first character is not ALPHA or '*'"); + return Err(Error::new( + "serialize_token: first character is not ALPHA or '*'", + )); } } } @@ -287,7 +297,7 @@ impl Serializer { .bytes() .any(|c| !(utils::is_tchar(c) || c == b':' || c == b'/')) { - return Err("serialize_token: disallowed character"); + return Err(Error::new("serialize_token: disallowed character")); } output.push_str(value); diff --git a/src/test_parser.rs b/src/test_parser.rs index 631ff96..dbcd4c7 100644 --- a/src/test_parser.rs +++ b/src/test_parser.rs @@ -1,12 +1,12 @@ use crate::{ - BareItem, Decimal, Dictionary, FromStr, InnerList, Item, List, Num, Parameters, ParseMore, - Parser, + BareItem, Decimal, Dictionary, Error, FromStr, InnerList, Item, List, Num, Parameters, + ParseMore, Parser, }; -use std::error::Error; +use std::error::Error as StdError; use std::iter::FromIterator; #[test] -fn parse() -> Result<(), Box> { +fn parse() -> Result<(), Box> { let input = "\"some_value\""; let parsed_item = Item::new(BareItem::String("some_value".to_owned())); let expected = parsed_item; @@ -21,26 +21,26 @@ fn parse() -> Result<(), Box> { } #[test] -fn parse_errors() -> Result<(), Box> { +fn parse_errors() -> Result<(), Box> { let input = "\"some_value¢\""; assert_eq!( - Err("parse_string: invalid string character"), + Err(Error::new("parse_string: invalid string character")), Parser::from_str(input).parse_item() ); let input = "\"some_value\" trailing_text"; assert_eq!( - Err("parse: trailing characters after parsed value"), + Err(Error::new("parse: trailing characters after parsed value")), Parser::from_str(input).parse_item() ); assert_eq!( - Err("parse_bare_item: empty item"), + Err(Error::new("parse_bare_item: empty item")), Parser::from_str("").parse_item() ); Ok(()) } #[test] -fn parse_list_of_numbers() -> Result<(), Box> { +fn parse_list_of_numbers() -> Result<(), Box> { let input = "1,42"; let item1 = Item::new(1.into()); let item2 = Item::new(42.into()); @@ -50,7 +50,7 @@ fn parse_list_of_numbers() -> Result<(), Box> { } #[test] -fn parse_list_with_multiple_spaces() -> Result<(), Box> { +fn parse_list_with_multiple_spaces() -> Result<(), Box> { let input = "1 , 42"; let item1 = Item::new(1.into()); let item2 = Item::new(42.into()); @@ -60,7 +60,7 @@ fn parse_list_with_multiple_spaces() -> Result<(), Box> { } #[test] -fn parse_list_of_lists() -> Result<(), Box> { +fn parse_list_of_lists() -> Result<(), Box> { let input = "(1 2), (42 43)"; let item1 = Item::new(1.into()); let item2 = Item::new(2.into()); @@ -74,7 +74,7 @@ fn parse_list_of_lists() -> Result<(), Box> { } #[test] -fn parse_list_empty_inner_list() -> Result<(), Box> { +fn parse_list_empty_inner_list() -> Result<(), Box> { let input = "()"; let inner_list = InnerList::new(vec![]); let expected_list: List = vec![inner_list.into()]; @@ -83,7 +83,7 @@ fn parse_list_empty_inner_list() -> Result<(), Box> { } #[test] -fn parse_list_empty() -> Result<(), Box> { +fn parse_list_empty() -> Result<(), Box> { let input = ""; let expected_list: List = vec![]; assert_eq!(expected_list, Parser::from_str(input).parse_list()?); @@ -91,7 +91,7 @@ fn parse_list_empty() -> Result<(), Box> { } #[test] -fn parse_list_of_lists_with_param_and_spaces() -> Result<(), Box> { +fn parse_list_of_lists_with_param_and_spaces() -> Result<(), Box> { let input = "( 1 42 ); k=*"; let item1 = Item::new(1.into()); let item2 = Item::new(42.into()); @@ -104,7 +104,7 @@ fn parse_list_of_lists_with_param_and_spaces() -> Result<(), Box> { } #[test] -fn parse_list_of_items_and_lists_with_param() -> Result<(), Box> { +fn parse_list_of_items_and_lists_with_param() -> Result<(), Box> { let input = "12, 14, (a b); param=\"param_value_1\", ()"; let item1 = Item::new(12.into()); let item2 = Item::new(14.into()); @@ -127,52 +127,54 @@ fn parse_list_of_items_and_lists_with_param() -> Result<(), Box> { } #[test] -fn parse_list_errors() -> Result<(), Box> { +fn parse_list_errors() -> Result<(), Box> { let input = ","; assert_eq!( - Err("parse_bare_item: item type can't be identified"), + Err(Error::new("parse_bare_item: item type can't be identified")), Parser::from_str(input).parse_list() ); let input = "a, b c"; assert_eq!( - Err("parse_list: trailing characters after list member"), + Err(Error::new( + "parse_list: trailing characters after list member" + )), Parser::from_str(input).parse_list() ); let input = "a,"; assert_eq!( - Err("parse_list: trailing comma"), + Err(Error::new("parse_list: trailing comma")), Parser::from_str(input).parse_list() ); let input = "a , "; assert_eq!( - Err("parse_list: trailing comma"), + Err(Error::new("parse_list: trailing comma")), Parser::from_str(input).parse_list() ); let input = "a\t \t ,\t "; assert_eq!( - Err("parse_list: trailing comma"), + Err(Error::new("parse_list: trailing comma")), Parser::from_str(input).parse_list() ); let input = "a\t\t,\t\t\t"; assert_eq!( - Err("parse_list: trailing comma"), + Err(Error::new("parse_list: trailing comma")), Parser::from_str(input).parse_list() ); let input = "(a b),"; assert_eq!( - Err("parse_list: trailing comma"), + Err(Error::new("parse_list: trailing comma")), Parser::from_str(input).parse_list() ); let input = "(1, 2, (a b)"; assert_eq!( - Err("parse_inner_list: bad delimitation"), + Err(Error::new("parse_inner_list: bad delimitation")), Parser::from_str(input).parse_list() ); @@ -180,17 +182,19 @@ fn parse_list_errors() -> Result<(), Box> { } #[test] -fn parse_inner_list_errors() -> Result<(), Box> { +fn parse_inner_list_errors() -> Result<(), Box> { let input = "c b); a=1"; assert_eq!( - Err("parse_inner_list: input does not start with '('"), + Err(Error::new( + "parse_inner_list: input does not start with '('" + )), Parser::from_str(input).parse_inner_list() ); Ok(()) } #[test] -fn parse_inner_list_with_param_and_spaces() -> Result<(), Box> { +fn parse_inner_list_with_param_and_spaces() -> Result<(), Box> { let input = "(c b); a=1"; let inner_list_param = Parameters::from_iter(vec![("a".to_owned(), 1.into())]); @@ -202,14 +206,14 @@ fn parse_inner_list_with_param_and_spaces() -> Result<(), Box> { } #[test] -fn parse_item_int_with_space() -> Result<(), Box> { +fn parse_item_int_with_space() -> Result<(), Box> { let input = "12 "; assert_eq!(Item::new(12.into()), Parser::from_str(input).parse_item()?); Ok(()) } #[test] -fn parse_item_decimal_with_bool_param_and_space() -> Result<(), Box> { +fn parse_item_decimal_with_bool_param_and_space() -> Result<(), Box> { let input = "12.35;a "; let param = Parameters::from_iter(vec![("a".to_owned(), BareItem::Boolean(true))]); assert_eq!( @@ -220,7 +224,7 @@ fn parse_item_decimal_with_bool_param_and_space() -> Result<(), Box> } #[test] -fn parse_item_number_with_param() -> Result<(), Box> { +fn parse_item_number_with_param() -> Result<(), Box> { let param = Parameters::from_iter(vec![("a1".to_owned(), BareItem::Token("*".to_owned()))]); assert_eq!( Item::with_params(BareItem::String("12.35".to_owned()), param), @@ -230,37 +234,39 @@ fn parse_item_number_with_param() -> Result<(), Box> { } #[test] -fn parse_item_errors() -> Result<(), Box> { +fn parse_item_errors() -> Result<(), Box> { assert_eq!( - Err("parse_bare_item: empty item"), + Err(Error::new("parse_bare_item: empty item")), Parser::from_str("").parse_item() ); Ok(()) } #[test] -fn parse_dict_empty() -> Result<(), Box> { +fn parse_dict_empty() -> Result<(), Box> { assert_eq!(Dictionary::new(), Parser::from_str("").parse_dictionary()?); Ok(()) } #[test] -fn parse_dict_errors() -> Result<(), Box> { +fn parse_dict_errors() -> Result<(), Box> { let input = "abc=123;a=1;b=2 def"; assert_eq!( - Err("parse_dict: trailing characters after dictionary member"), + Err(Error::new( + "parse_dict: trailing characters after dictionary member" + )), Parser::from_str(input).parse_dictionary() ); let input = "abc=123;a=1,"; assert_eq!( - Err("parse_dict: trailing comma"), + Err(Error::new("parse_dict: trailing comma")), Parser::from_str(input).parse_dictionary() ); Ok(()) } #[test] -fn parse_dict_with_spaces_and_params() -> Result<(), Box> { +fn parse_dict_with_spaces_and_params() -> Result<(), Box> { let input = "abc=123;a=1;b=2, def=456, ghi=789;q=9;r=\"+w\""; let item1_params = Parameters::from_iter(vec![("a".to_owned(), 1.into()), ("b".to_owned(), 2.into())]); @@ -284,7 +290,7 @@ fn parse_dict_with_spaces_and_params() -> Result<(), Box> { } #[test] -fn parse_dict_empty_value() -> Result<(), Box> { +fn parse_dict_empty_value() -> Result<(), Box> { let input = "a=()"; let inner_list = InnerList::new(vec![]); let expected_dict = Dictionary::from_iter(vec![("a".to_owned(), inner_list.into())]); @@ -293,7 +299,7 @@ fn parse_dict_empty_value() -> Result<(), Box> { } #[test] -fn parse_dict_with_token_param() -> Result<(), Box> { +fn parse_dict_with_token_param() -> Result<(), Box> { let input = "a=1, b;foo=*, c=3"; let item2_params = Parameters::from_iter(vec![("foo".to_owned(), BareItem::Token("*".to_owned()))]); @@ -310,7 +316,7 @@ fn parse_dict_with_token_param() -> Result<(), Box> { } #[test] -fn parse_dict_multiple_spaces() -> Result<(), Box> { +fn parse_dict_multiple_spaces() -> Result<(), Box> { // input1, input2, input3 must be parsed into the same structure let item1 = Item::new(1.into()); let item2 = Item::new(2.into()); @@ -330,7 +336,7 @@ fn parse_dict_multiple_spaces() -> Result<(), Box> { } #[test] -fn parse_bare_item() -> Result<(), Box> { +fn parse_bare_item() -> Result<(), Box> { assert_eq!( BareItem::Boolean(false), Parser::from_str("?0").parse_bare_item()? @@ -355,24 +361,24 @@ fn parse_bare_item() -> Result<(), Box> { } #[test] -fn parse_bare_item_errors() -> Result<(), Box> { +fn parse_bare_item_errors() -> Result<(), Box> { assert_eq!( - Err("parse_bare_item: item type can't be identified"), + Err(Error::new("parse_bare_item: item type can't be identified")), Parser::from_str("!?0").parse_bare_item() ); assert_eq!( - Err("parse_bare_item: item type can't be identified"), + Err(Error::new("parse_bare_item: item type can't be identified")), Parser::from_str("_11abc").parse_bare_item() ); assert_eq!( - Err("parse_bare_item: item type can't be identified"), + Err(Error::new("parse_bare_item: item type can't be identified")), Parser::from_str(" ").parse_bare_item() ); Ok(()) } #[test] -fn parse_bool() -> Result<(), Box> { +fn parse_bool() -> Result<(), Box> { let mut parser = Parser::from_str("?0gk"); assert_eq!(false, parser.parse_bool()?); assert_eq!(parser.remaining(), b"gk"); @@ -383,20 +389,20 @@ fn parse_bool() -> Result<(), Box> { } #[test] -fn parse_bool_errors() -> Result<(), Box> { +fn parse_bool_errors() -> Result<(), Box> { assert_eq!( - Err("parse_bool: first character is not '?'"), + Err(Error::new("parse_bool: first character is not '?'")), Parser::from_str("").parse_bool() ); assert_eq!( - Err("parse_bool: invalid variant"), + Err(Error::new("parse_bool: invalid variant")), Parser::from_str("?").parse_bool() ); Ok(()) } #[test] -fn parse_string() -> Result<(), Box> { +fn parse_string() -> Result<(), Box> { let mut parser = Parser::from_str("\"some string\" ;not string"); assert_eq!("some string".to_owned(), parser.parse_string()?); assert_eq!(parser.remaining(), " ;not string".as_bytes()); @@ -418,32 +424,32 @@ fn parse_string() -> Result<(), Box> { } #[test] -fn parse_string_errors() -> Result<(), Box> { +fn parse_string_errors() -> Result<(), Box> { assert_eq!( - Err("parse_string: first character is not '\"'"), + Err(Error::new("parse_string: first character is not '\"'")), Parser::from_str("test").parse_string() ); assert_eq!( - Err("parse_string: last input character is '\\'"), + Err(Error::new("parse_string: last input character is '\\'")), Parser::from_str("\"\\").parse_string() ); assert_eq!( - Err("parse_string: disallowed character after '\\'"), + Err(Error::new("parse_string: disallowed character after '\\'")), Parser::from_str("\"\\l\"").parse_string() ); assert_eq!( - Err("parse_string: invalid string character"), + Err(Error::new("parse_string: invalid string character")), Parser::from_str("\"\u{1f}\"").parse_string() ); assert_eq!( - Err("parse_string: no closing '\"'"), + Err(Error::new("parse_string: no closing '\"'")), Parser::from_str("\"smth").parse_string() ); Ok(()) } #[test] -fn parse_token() -> Result<(), Box> { +fn parse_token() -> Result<(), Box> { let mut parser = Parser::from_str("*some:token}not token"); assert_eq!("*some:token".to_owned(), parser.parse_token()?); assert_eq!(parser.remaining(), b"}not token"); @@ -475,27 +481,31 @@ fn parse_token() -> Result<(), Box> { } #[test] -fn parse_token_errors() -> Result<(), Box> { +fn parse_token_errors() -> Result<(), Box> { let mut parser = Parser::from_str("765token"); assert_eq!( - Err("parse_token: first character is not ALPHA or '*'"), + Err(Error::new( + "parse_token: first character is not ALPHA or '*'" + )), parser.parse_token() ); assert_eq!(parser.remaining(), b"765token"); assert_eq!( - Err("parse_token: first character is not ALPHA or '*'"), + Err(Error::new( + "parse_token: first character is not ALPHA or '*'" + )), Parser::from_str("7token").parse_token() ); assert_eq!( - Err("parse_token: empty input string"), + Err(Error::new("parse_token: empty input string")), Parser::from_str("").parse_token() ); Ok(()) } #[test] -fn parse_byte_sequence() -> Result<(), Box> { +fn parse_byte_sequence() -> Result<(), Box> { let mut parser = Parser::from_str(":aGVsbG8:rest_of_str"); assert_eq!( "hello".to_owned().into_bytes(), @@ -523,24 +533,24 @@ fn parse_byte_sequence() -> Result<(), Box> { } #[test] -fn parse_byte_sequence_errors() -> Result<(), Box> { +fn parse_byte_sequence_errors() -> Result<(), Box> { assert_eq!( - Err("parse_byte_seq: first char is not ':'"), + Err(Error::new("parse_byte_seq: first char is not ':'")), Parser::from_str("aGVsbG8").parse_byte_sequence() ); assert_eq!( - Err("parse_byte_seq: decoding error"), + Err(Error::new("parse_byte_seq: decoding error")), Parser::from_str(":aGVsb G8=:").parse_byte_sequence() ); assert_eq!( - Err("parse_byte_seq: no closing ':'"), + Err(Error::new("parse_byte_seq: no closing ':'")), Parser::from_str(":aGVsbG8=").parse_byte_sequence() ); Ok(()) } #[test] -fn parse_number_int() -> Result<(), Box> { +fn parse_number_int() -> Result<(), Box> { let mut parser = Parser::from_str("-733333333332d.14"); assert_eq!(Num::Integer(-733333333332), parser.parse_number()?); assert_eq!(parser.remaining(), b"d.14"); @@ -573,7 +583,7 @@ fn parse_number_int() -> Result<(), Box> { } #[test] -fn parse_number_decimal() -> Result<(), Box> { +fn parse_number_decimal() -> Result<(), Box> { let mut parser = Parser::from_str("00.42 test string"); assert_eq!( Num::Decimal(Decimal::from_str("0.42")?), @@ -614,68 +624,81 @@ fn parse_number_decimal() -> Result<(), Box> { } #[test] -fn parse_number_errors() -> Result<(), Box> { +fn parse_number_errors() -> Result<(), Box> { let mut parser = Parser::from_str(":aGVsbG8:rest"); - assert_eq!(Err("parse_number: expected digit"), parser.parse_number()); + assert_eq!( + Err(Error::new("parse_number: expected digit")), + parser.parse_number() + ); assert_eq!(parser.remaining(), b":aGVsbG8:rest"); let mut parser = Parser::from_str("-11.5555 test string"); assert_eq!( - Err("parse_number: too many digits after decimal point"), + Err(Error::new( + "parse_number: too many digits after decimal point" + )), parser.parse_number() ); assert_eq!(parser.remaining(), b"5 test string"); assert_eq!( - Err("parse_number: expected digit"), + Err(Error::new("parse_number: expected digit")), Parser::from_str("--0").parse_number() ); assert_eq!( - Err("parse_number: too many digits before decimal point"), + Err(Error::new( + "parse_number: too many digits before decimal point" + )), Parser::from_str("1999999999999.1").parse_number() ); assert_eq!( - Err("parse_number: trailing decimal point"), + Err(Error::new("parse_number: trailing decimal point")), Parser::from_str("19888899999.").parse_number() ); assert_eq!( - Err("parse_number: too many digits"), + Err(Error::new("parse_number: too many digits")), Parser::from_str("1999999999999999").parse_number() ); assert_eq!( - Err("parse_number: too many digits after decimal point"), + Err(Error::new( + "parse_number: too many digits after decimal point" + )), Parser::from_str("19999999999.99991").parse_number() ); assert_eq!( - Err("parse_number: expected digit"), + Err(Error::new("parse_number: expected digit")), Parser::from_str("- 42").parse_number() ); assert_eq!( - Err("parse_number: expected digit"), + Err(Error::new("parse_number: expected digit")), Parser::from_str("- 42").parse_number() ); assert_eq!( - Err("parse_number: trailing decimal point"), + Err(Error::new("parse_number: trailing decimal point")), Parser::from_str("1..4").parse_number() ); assert_eq!( - Err("parse_number: expected digit"), + Err(Error::new("parse_number: expected digit")), Parser::from_str("-").parse_number() ); assert_eq!( - Err("parse_number: trailing decimal point"), + Err(Error::new("parse_number: trailing decimal point")), Parser::from_str("-5. 14").parse_number() ); assert_eq!( - Err("parse_number: trailing decimal point"), + Err(Error::new("parse_number: trailing decimal point")), Parser::from_str("7. 1").parse_number() ); assert_eq!( - Err("parse_number: too many digits after decimal point"), + Err(Error::new( + "parse_number: too many digits after decimal point" + )), Parser::from_str("-7.3333333333").parse_number() ); assert_eq!( - Err("parse_number: too many digits before decimal point"), + Err(Error::new( + "parse_number: too many digits before decimal point" + )), Parser::from_str("-7333333333323.12").parse_number() ); @@ -683,7 +706,7 @@ fn parse_number_errors() -> Result<(), Box> { } #[test] -fn parse_params_string() -> Result<(), Box> { +fn parse_params_string() -> Result<(), Box> { let input = ";b=\"param_val\""; let expected = Parameters::from_iter(vec![( "b".to_owned(), @@ -694,7 +717,7 @@ fn parse_params_string() -> Result<(), Box> { } #[test] -fn parse_params_bool() -> Result<(), Box> { +fn parse_params_bool() -> Result<(), Box> { let input = ";b;a"; let expected = Parameters::from_iter(vec![ ("b".to_owned(), BareItem::Boolean(true)), @@ -705,7 +728,7 @@ fn parse_params_bool() -> Result<(), Box> { } #[test] -fn parse_params_mixed_types() -> Result<(), Box> { +fn parse_params_mixed_types() -> Result<(), Box> { let input = ";key1=?0;key2=746.15"; let expected = Parameters::from_iter(vec![ ("key1".to_owned(), BareItem::Boolean(false)), @@ -716,7 +739,7 @@ fn parse_params_mixed_types() -> Result<(), Box> { } #[test] -fn parse_params_with_spaces() -> Result<(), Box> { +fn parse_params_with_spaces() -> Result<(), Box> { let input = "; key1=?0; key2=11111"; let expected = Parameters::from_iter(vec![ ("key1".to_owned(), BareItem::Boolean(false)), @@ -727,7 +750,7 @@ fn parse_params_with_spaces() -> Result<(), Box> { } #[test] -fn parse_params_empty() -> Result<(), Box> { +fn parse_params_empty() -> Result<(), Box> { assert_eq!( Parameters::new(), Parser::from_str(" key1=?0; key2=11111").parse_parameters()? @@ -742,7 +765,7 @@ fn parse_params_empty() -> Result<(), Box> { } #[test] -fn parse_key() -> Result<(), Box> { +fn parse_key() -> Result<(), Box> { assert_eq!("a".to_owned(), Parser::from_str("a=1").parse_key()?); assert_eq!("a1".to_owned(), Parser::from_str("a1=10").parse_key()?); assert_eq!("*1".to_owned(), Parser::from_str("*1=10").parse_key()?); @@ -751,16 +774,18 @@ fn parse_key() -> Result<(), Box> { } #[test] -fn parse_key_errors() -> Result<(), Box> { +fn parse_key_errors() -> Result<(), Box> { assert_eq!( - Err("parse_key: first character is not lcalpha or '*'"), + Err(Error::new( + "parse_key: first character is not lcalpha or '*'" + )), Parser::from_str("[*f=10").parse_key() ); Ok(()) } #[test] -fn parse_more_list() -> Result<(), Box> { +fn parse_more_list() -> Result<(), Box> { let item1 = Item::new(1.into()); let item2 = Item::new(2.into()); let item3 = Item::new(42.into()); @@ -774,7 +799,7 @@ fn parse_more_list() -> Result<(), Box> { } #[test] -fn parse_more_dict() -> Result<(), Box> { +fn parse_more_dict() -> Result<(), Box> { let item2_params = Parameters::from_iter(vec![("foo".to_owned(), BareItem::Token("*".to_owned()))]); let item1 = Item::new(1.into()); @@ -793,7 +818,7 @@ fn parse_more_dict() -> Result<(), Box> { } #[test] -fn parse_more_errors() -> Result<(), Box> { +fn parse_more_errors() -> Result<(), Box> { let parsed_dict_header = Parser::from_str("a=1, b;foo=*") .parse_dictionary()? .parse_more(",a".as_bytes()); diff --git a/src/test_serializer.rs b/src/test_serializer.rs index 6025fa7..b79f7f9 100644 --- a/src/test_serializer.rs +++ b/src/test_serializer.rs @@ -1,32 +1,36 @@ use crate::serializer::Serializer; use crate::FromStr; use crate::SerializeValue; -use crate::{BareItem, Decimal, Dictionary, InnerList, Item, List, Parameters}; -use std::error::Error; +use crate::{BareItem, Decimal, Dictionary, Error, InnerList, Item, List, Parameters}; +use std::error::Error as StdError; use std::iter::FromIterator; #[test] -fn serialize_value_empty_dict() -> Result<(), Box> { +fn serialize_value_empty_dict() -> Result<(), Box> { let dict_field_value = Dictionary::new(); assert_eq!( - Err("serialize_dictionary: serializing empty field is not allowed"), + Err(Error::new( + "serialize_dictionary: serializing empty field is not allowed" + )), dict_field_value.serialize_value() ); Ok(()) } #[test] -fn serialize_value_empty_list() -> Result<(), Box> { +fn serialize_value_empty_list() -> Result<(), Box> { let list_field_value = List::new(); assert_eq!( - Err("serialize_list: serializing empty field is not allowed"), + Err(Error::new( + "serialize_list: serializing empty field is not allowed" + )), list_field_value.serialize_value() ); Ok(()) } #[test] -fn serialize_value_list_mixed_members_with_params() -> Result<(), Box> { +fn serialize_value_list_mixed_members_with_params() -> Result<(), Box> { let item1 = Item::new(Decimal::from_str("42.4568")?.into()); let item2_param = Parameters::from_iter(vec![("itm2_p".to_owned(), BareItem::Boolean(true))]); let item2 = Item::with_params(17.into(), item2_param); @@ -55,30 +59,34 @@ fn serialize_value_list_mixed_members_with_params() -> Result<(), Box } #[test] -fn serialize_value_errors() -> Result<(), Box> { +fn serialize_value_errors() -> Result<(), Box> { let disallowed_item = Item::new(BareItem::String("non-ascii text 🐹".into())); assert_eq!( - Err("serialize_string: non-ascii character"), + Err(Error::new("serialize_string: non-ascii character")), disallowed_item.serialize_value() ); let disallowed_item = Item::new(Decimal::from_str("12345678912345.123")?.into()); assert_eq!( - Err("serialize_decimal: integer component > 12 digits"), + Err(Error::new( + "serialize_decimal: integer component > 12 digits" + )), disallowed_item.serialize_value() ); let param_with_disallowed_key = Parameters::from_iter(vec![("_key".to_owned(), 13.into())]); let disallowed_item = Item::with_params(12.into(), param_with_disallowed_key); assert_eq!( - Err("serialize_key: first character is not lcalpha or '*'"), + Err(Error::new( + "serialize_key: first character is not lcalpha or '*'" + )), disallowed_item.serialize_value() ); Ok(()) } #[test] -fn serialize_item_byteseq_with_param() -> Result<(), Box> { +fn serialize_item_byteseq_with_param() -> Result<(), Box> { let mut buf = String::new(); let item_param = ("a".to_owned(), BareItem::Token("*ab_1".into())); @@ -90,7 +98,7 @@ fn serialize_item_byteseq_with_param() -> Result<(), Box> { } #[test] -fn serialize_item_without_params() -> Result<(), Box> { +fn serialize_item_without_params() -> Result<(), Box> { let mut buf = String::new(); let item = Item::new(1.into()); Serializer::serialize_item(&item, &mut buf)?; @@ -99,7 +107,7 @@ fn serialize_item_without_params() -> Result<(), Box> { } #[test] -fn serialize_item_with_bool_true_param() -> Result<(), Box> { +fn serialize_item_with_bool_true_param() -> Result<(), Box> { let mut buf = String::new(); let param = Parameters::from_iter(vec![("a".to_owned(), BareItem::Boolean(true))]); let item = Item::with_params(Decimal::from_str("12.35")?.into(), param); @@ -109,7 +117,7 @@ fn serialize_item_with_bool_true_param() -> Result<(), Box> { } #[test] -fn serialize_item_with_token_param() -> Result<(), Box> { +fn serialize_item_with_token_param() -> Result<(), Box> { let mut buf = String::new(); let param = Parameters::from_iter(vec![("a1".to_owned(), BareItem::Token("*tok".to_owned()))]); let item = Item::with_params(BareItem::String("12.35".to_owned()), param); @@ -119,7 +127,7 @@ fn serialize_item_with_token_param() -> Result<(), Box> { } #[test] -fn serialize_integer() -> Result<(), Box> { +fn serialize_integer() -> Result<(), Box> { let mut buf = String::new(); Serializer::serialize_integer(-12, &mut buf)?; assert_eq!("-12", &buf); @@ -139,23 +147,23 @@ fn serialize_integer() -> Result<(), Box> { } #[test] -fn serialize_integer_errors() -> Result<(), Box> { +fn serialize_integer_errors() -> Result<(), Box> { let mut buf = String::new(); assert_eq!( - Err("serialize_integer: integer is out of range"), + Err(Error::new("serialize_integer: integer is out of range")), Serializer::serialize_integer(1_000_000_000_000_000, &mut buf) ); buf.clear(); assert_eq!( - Err("serialize_integer: integer is out of range"), + Err(Error::new("serialize_integer: integer is out of range")), Serializer::serialize_integer(-1_000_000_000_000_000, &mut buf) ); Ok(()) } #[test] -fn serialize_decimal() -> Result<(), Box> { +fn serialize_decimal() -> Result<(), Box> { let mut buf = String::new(); Serializer::serialize_decimal(Decimal::from_str("-99.1346897")?, &mut buf)?; assert_eq!("-99.135", &buf); @@ -198,17 +206,19 @@ fn serialize_decimal() -> Result<(), Box> { } #[test] -fn serialize_decimal_errors() -> Result<(), Box> { +fn serialize_decimal_errors() -> Result<(), Box> { let mut buf = String::new(); assert_eq!( - Err("serialize_decimal: integer component > 12 digits"), + Err(Error::new( + "serialize_decimal: integer component > 12 digits" + )), Serializer::serialize_decimal(Decimal::from_str("1371212121121.1")?, &mut buf) ); Ok(()) } #[test] -fn serialize_string() -> Result<(), Box> { +fn serialize_string() -> Result<(), Box> { let mut buf = String::new(); Serializer::serialize_string("1.1 text", &mut buf)?; assert_eq!("\"1.1 text\"", &buf); @@ -236,31 +246,31 @@ fn serialize_string() -> Result<(), Box> { } #[test] -fn serialize_string_errors() -> Result<(), Box> { +fn serialize_string_errors() -> Result<(), Box> { let mut buf = String::new(); assert_eq!( - Err("serialize_string: not a visible character"), + Err(Error::new("serialize_string: not a visible character")), Serializer::serialize_string("text \x00", &mut buf) ); assert_eq!( - Err("serialize_string: not a visible character"), + Err(Error::new("serialize_string: not a visible character")), Serializer::serialize_string("text \x1f", &mut buf) ); assert_eq!( - Err("serialize_string: not a visible character"), + Err(Error::new("serialize_string: not a visible character")), Serializer::serialize_string("text \x7f", &mut buf) ); assert_eq!( - Err("serialize_string: non-ascii character"), + Err(Error::new("serialize_string: non-ascii character")), Serializer::serialize_string("рядок", &mut buf) ); Ok(()) } #[test] -fn serialize_token() -> Result<(), Box> { +fn serialize_token() -> Result<(), Box> { let mut buf = String::new(); Serializer::serialize_token("*", &mut buf)?; assert_eq!("*", &buf); @@ -280,30 +290,32 @@ fn serialize_token() -> Result<(), Box> { } #[test] -fn serialize_token_errors() -> Result<(), Box> { +fn serialize_token_errors() -> Result<(), Box> { let mut buf = String::new(); assert_eq!( - Err("serialize_token: token is empty"), + Err(Error::new("serialize_token: token is empty")), Serializer::serialize_token("", &mut buf) ); assert_eq!( - Err("serialize_token: first character is not ALPHA or '*'"), + Err(Error::new( + "serialize_token: first character is not ALPHA or '*'" + )), Serializer::serialize_token("#some", &mut buf) ); assert_eq!( - Err("serialize_token: disallowed character"), + Err(Error::new("serialize_token: disallowed character")), Serializer::serialize_token("s ", &mut buf) ); assert_eq!( - Err("serialize_token: disallowed character"), + Err(Error::new("serialize_token: disallowed character")), Serializer::serialize_token("abc:de\t", &mut buf) ); Ok(()) } #[test] -fn serialize_byte_sequence() -> Result<(), Box> { +fn serialize_byte_sequence() -> Result<(), Box> { let mut buf = String::new(); Serializer::serialize_byte_sequence("hello".as_bytes(), &mut buf)?; assert_eq!(":aGVsbG8=:", &buf); @@ -340,7 +352,7 @@ fn serialize_byte_sequence() -> Result<(), Box> { } #[test] -fn serialize_bool() -> Result<(), Box> { +fn serialize_bool() -> Result<(), Box> { let mut buf = String::new(); Serializer::serialize_bool(true, &mut buf)?; assert_eq!("?1", &buf); @@ -352,7 +364,7 @@ fn serialize_bool() -> Result<(), Box> { } #[test] -fn serialize_params_bool() -> Result<(), Box> { +fn serialize_params_bool() -> Result<(), Box> { let mut buf = String::new(); let input = Parameters::from_iter(vec![ @@ -366,7 +378,7 @@ fn serialize_params_bool() -> Result<(), Box> { } #[test] -fn serialize_params_string() -> Result<(), Box> { +fn serialize_params_string() -> Result<(), Box> { let mut buf = String::new(); let input = Parameters::from_iter(vec![( @@ -379,7 +391,7 @@ fn serialize_params_string() -> Result<(), Box> { } #[test] -fn serialize_params_numbers() -> Result<(), Box> { +fn serialize_params_numbers() -> Result<(), Box> { let mut buf = String::new(); let input = Parameters::from_iter(vec![ @@ -392,7 +404,7 @@ fn serialize_params_numbers() -> Result<(), Box> { } #[test] -fn serialize_params_mixed_types() -> Result<(), Box> { +fn serialize_params_mixed_types() -> Result<(), Box> { let mut buf = String::new(); let input = Parameters::from_iter(vec![ @@ -405,7 +417,7 @@ fn serialize_params_mixed_types() -> Result<(), Box> { } #[test] -fn serialize_key() -> Result<(), Box> { +fn serialize_key() -> Result<(), Box> { let mut buf = String::new(); Serializer::serialize_key("*a_fg", &mut buf)?; assert_eq!("*a_fg", &buf); @@ -426,30 +438,34 @@ fn serialize_key() -> Result<(), Box> { } #[test] -fn serialize_key_errors() -> Result<(), Box> { +fn serialize_key_errors() -> Result<(), Box> { let mut buf = String::new(); assert_eq!( - Err("serialize_key: key is empty"), + Err(Error::new("serialize_key: key is empty")), Serializer::serialize_key("", &mut buf) ); assert_eq!( - Err("serialize_key: disallowed character in input"), + Err(Error::new("serialize_key: disallowed character in input")), Serializer::serialize_key("aND", &mut buf) ); assert_eq!( - Err("serialize_key: first character is not lcalpha or '*'"), + Err(Error::new( + "serialize_key: first character is not lcalpha or '*'" + )), Serializer::serialize_key("_key", &mut buf) ); assert_eq!( - Err("serialize_key: first character is not lcalpha or '*'"), + Err(Error::new( + "serialize_key: first character is not lcalpha or '*'" + )), Serializer::serialize_key("7key", &mut buf) ); Ok(()) } #[test] -fn serialize_list_of_items_and_inner_list() -> Result<(), Box> { +fn serialize_list_of_items_and_inner_list() -> Result<(), Box> { let mut buf = String::new(); let item1 = Item::new(12.into()); @@ -469,7 +485,7 @@ fn serialize_list_of_items_and_inner_list() -> Result<(), Box> { } #[test] -fn serialize_list_of_lists() -> Result<(), Box> { +fn serialize_list_of_lists() -> Result<(), Box> { let mut buf = String::new(); let item1 = Item::new(1.into()); @@ -486,7 +502,7 @@ fn serialize_list_of_lists() -> Result<(), Box> { } #[test] -fn serialize_list_with_bool_item_and_bool_params() -> Result<(), Box> { +fn serialize_list_with_bool_item_and_bool_params() -> Result<(), Box> { let mut buf = String::new(); let item1_params = Parameters::from_iter(vec![ @@ -503,7 +519,7 @@ fn serialize_list_with_bool_item_and_bool_params() -> Result<(), Box> } #[test] -fn serialize_dictionary_with_params() -> Result<(), Box> { +fn serialize_dictionary_with_params() -> Result<(), Box> { let mut buf = String::new(); let item1_params = Parameters::from_iter(vec![ @@ -532,7 +548,7 @@ fn serialize_dictionary_with_params() -> Result<(), Box> { } #[test] -fn serialize_dict_empty_member_value() -> Result<(), Box> { +fn serialize_dict_empty_member_value() -> Result<(), Box> { let mut buf = String::new(); let inner_list = InnerList::new(vec![]); diff --git a/tests/specification_tests.rs b/tests/specification_tests.rs index 34e825a..a5d6f8f 100644 --- a/tests/specification_tests.rs +++ b/tests/specification_tests.rs @@ -34,7 +34,7 @@ enum FieldType { Dict(Dictionary), } impl FieldType { - fn serialize(&self) -> Result { + fn serialize(&self) -> Result { match self { FieldType::Item(value) => value.serialize_value(), FieldType::List(value) => value.serialize_value(),