diff --git a/instant-xml/src/impls.rs b/instant-xml/src/impls.rs index ce8378b..cd054a1 100644 --- a/instant-xml/src/impls.rs +++ b/instant-xml/src/impls.rs @@ -317,6 +317,7 @@ fn decode(input: &str) -> Cow<'_, str> { Cow::Owned(result) } +const VEC_LIST_TAG: &str = "list"; const VEC_ELEMENT_TAG: &str = "element"; impl<'xml, T> FromXml<'xml> for Vec @@ -325,10 +326,11 @@ where { fn deserialize<'cx>(deserializer: &'cx mut Deserializer<'cx, 'xml>) -> Result { let mut result = Self::new(); + let kind = >::KIND; while let Some(Ok(node)) = deserializer.next() { - match node { - Node::Open(data) => { + match (&kind, node) { + (Kind::Scalar, Node::Open(data)) => { let id = deserializer.element_id(&data)?; match id.name { @@ -339,6 +341,10 @@ where _ => return Err(Error::UnexpectedState), } } + (Kind::Vec | Kind::Element(_), Node::Open(data)) => { + let mut nested = deserializer.nested(data); + result.push(>::deserialize(&mut nested)?) + } _ => return Err(Error::UnexpectedState), } } @@ -357,11 +363,29 @@ where &self, serializer: &mut Serializer, ) -> Result<(), Error> { - for i in self { - let prefix = serializer.write_start(VEC_ELEMENT_TAG, "", false)?; - serializer.end_start()?; - i.serialize(serializer)?; - serializer.write_close(prefix, VEC_ELEMENT_TAG)?; + match ::KIND { + Kind::Element(_) => { + for i in self { + i.serialize(serializer)?; + } + } + Kind::Scalar => { + for i in self { + let prefix = serializer.write_start(VEC_ELEMENT_TAG, "", false)?; + serializer.end_start()?; + i.serialize(serializer)?; + serializer.write_close(prefix, VEC_ELEMENT_TAG)?; + } + } + // this would be a Vec>, where the internal field is unnamed + Kind::Vec => { + for i in self { + let prefix = serializer.write_start(VEC_LIST_TAG, "", false)?; + serializer.end_start()?; + i.serialize(serializer)?; + serializer.write_close(prefix, VEC_LIST_TAG)?; + } + } } Ok(()) diff --git a/instant-xml/tests/entities.rs b/instant-xml/tests/entities.rs index 77c92c8..5345098 100644 --- a/instant-xml/tests/entities.rs +++ b/instant-xml/tests/entities.rs @@ -13,6 +13,33 @@ struct StructSpecialEntities<'a> { vec: Vec, } +#[derive(Debug, PartialEq, Eq, FromXml, ToXml)] +#[xml(ns("URI"))] +struct VecEntities<'a> { + complex: Vec>, + list1: Vec, + list2: Vec>, +} + +#[test] +fn vec_entities() { + let serialized = r#"<>&"'adsad"strstr&onetwothreeabab"#; + + let instance = VecEntities { + complex: vec![StructSpecialEntities { + string: String::from("<>&\"'adsad\""), + str: "str", + cow: Cow::Owned("str&".to_string()), + vec: vec!["one".into(), "two".into(), "three".into()], + }], + list1: vec!["a".into(), "b".into()], + list2: vec![vec!["a".into(), "b".into()]], + }; + + assert_eq!(to_string(&instance).unwrap(), serialized); + assert_eq!(from_str(serialized), Ok(instance)); +} + #[test] fn escape_back() { assert_eq!(