Add support for Vec<T>
This commit is contained in:
parent
44f8a2cc6d
commit
dc9eb50e6c
|
@ -2,7 +2,7 @@ use std::borrow::Cow;
|
||||||
use std::fmt;
|
use std::fmt;
|
||||||
use std::str::FromStr;
|
use std::str::FromStr;
|
||||||
|
|
||||||
use crate::{Deserializer, Error, FromXml, Kind, Serializer, ToXml};
|
use crate::{de::Node, Deserializer, Error, FromXml, Id, Kind, Serializer, ToXml};
|
||||||
|
|
||||||
// Deserializer
|
// Deserializer
|
||||||
struct FromXmlStr<T: FromStr>(Option<T>);
|
struct FromXmlStr<T: FromStr>(Option<T>);
|
||||||
|
@ -316,3 +316,68 @@ fn decode(input: &str) -> Cow<'_, str> {
|
||||||
|
|
||||||
Cow::Owned(result)
|
Cow::Owned(result)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const VEC_TAG: &str = "list";
|
||||||
|
const VEC_ELEMENT_TAG: &str = "element";
|
||||||
|
|
||||||
|
impl<'xml, T> FromXml<'xml> for Vec<T>
|
||||||
|
where
|
||||||
|
T: FromXml<'xml>,
|
||||||
|
{
|
||||||
|
fn deserialize<'cx>(deserializer: &'cx mut Deserializer<'cx, 'xml>) -> Result<Self, Error> {
|
||||||
|
let mut result = Self::new();
|
||||||
|
|
||||||
|
while let Some(Ok(node)) = deserializer.next() {
|
||||||
|
match node {
|
||||||
|
Node::Open(data) => {
|
||||||
|
let id = deserializer.element_id(&data)?;
|
||||||
|
|
||||||
|
match id.name {
|
||||||
|
VEC_ELEMENT_TAG => {
|
||||||
|
let mut nested = deserializer.nested(data);
|
||||||
|
result.push(<T as FromXml<'xml>>::deserialize(&mut nested)?)
|
||||||
|
}
|
||||||
|
_ => return Err(Error::UnexpectedState),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
_ => return Err(Error::UnexpectedState),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Ok(result)
|
||||||
|
}
|
||||||
|
|
||||||
|
const KIND: Kind = Kind::Element(Id {
|
||||||
|
ns: "",
|
||||||
|
name: VEC_TAG,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<T> ToXml for Vec<T>
|
||||||
|
where
|
||||||
|
T: ToXml,
|
||||||
|
{
|
||||||
|
fn serialize<W: fmt::Write + ?Sized>(
|
||||||
|
&self,
|
||||||
|
serializer: &mut Serializer<W>,
|
||||||
|
) -> Result<(), Error> {
|
||||||
|
let prefix = serializer.write_start(VEC_TAG, "", false)?;
|
||||||
|
serializer.end_start()?;
|
||||||
|
|
||||||
|
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)?;
|
||||||
|
}
|
||||||
|
|
||||||
|
serializer.write_close(prefix, VEC_TAG)?;
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
|
const KIND: Kind = Kind::Element(Id {
|
||||||
|
ns: "",
|
||||||
|
name: VEC_TAG,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
|
@ -10,32 +10,34 @@ struct StructSpecialEntities<'a> {
|
||||||
string: String,
|
string: String,
|
||||||
str: &'a str,
|
str: &'a str,
|
||||||
cow: Cow<'a, str>,
|
cow: Cow<'a, str>,
|
||||||
|
vec: Vec<String>,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn escape_back() {
|
fn escape_back() {
|
||||||
assert_eq!(
|
assert_eq!(
|
||||||
from_str(
|
from_str(
|
||||||
"<StructSpecialEntities xmlns=\"URI\"><string><>&"'adsad"</string><str>str</str><cow>str&</cow></StructSpecialEntities>"
|
"<StructSpecialEntities xmlns=\"URI\"><string><>&"'adsad"</string><str>str</str><cow>str&</cow><list xmlns=\"\"><element xmlns=\"\">one</element><element xmlns=\"\">two</element><element xmlns=\"\">three</element></list></StructSpecialEntities>"
|
||||||
),
|
),
|
||||||
Ok(StructSpecialEntities {
|
Ok(StructSpecialEntities {
|
||||||
string: String::from("<>&\"'adsad\""),
|
string: String::from("<>&\"'adsad\""),
|
||||||
str: "str",
|
str: "str",
|
||||||
cow: Cow::Owned("str&".to_string()),
|
cow: Cow::Owned("str&".to_string()),
|
||||||
|
vec: vec!["one".into(), "two".into(), "three".into()]
|
||||||
})
|
})
|
||||||
);
|
);
|
||||||
|
|
||||||
// Wrong str char
|
// Wrong str char
|
||||||
assert_eq!(
|
assert_eq!(
|
||||||
from_str(
|
from_str(
|
||||||
"<StructSpecialEntities xmlns=\"URI\"><string><>&"'adsad"</string><str>str&</str></StructSpecialEntities>"
|
"<StructSpecialEntities xmlns=\"URI\"><string><>&"'adsad"</string><str>str&</str><list xmlns=\"\"><element xmlns=\"\">one</element><element xmlns=\"\">two</element><element xmlns=\"\">three</element></list></StructSpecialEntities>"
|
||||||
),
|
),
|
||||||
Err::<StructSpecialEntities, _>(Error::UnexpectedValue)
|
Err::<StructSpecialEntities, _>(Error::UnexpectedValue)
|
||||||
);
|
);
|
||||||
|
|
||||||
// Borrowed
|
// Borrowed
|
||||||
let escape_back = from_str::<StructSpecialEntities>(
|
let escape_back = from_str::<StructSpecialEntities>(
|
||||||
"<StructSpecialEntities xmlns=\"URI\"><string><>&"'adsad"</string><str>str</str><cow>str</cow></StructSpecialEntities>"
|
"<StructSpecialEntities xmlns=\"URI\"><string><>&"'adsad"</string><str>str</str><cow>str</cow><list xmlns=\"\"><element xmlns=\"\">one</element><element xmlns=\"\">two</element><element xmlns=\"\">three</element></list></StructSpecialEntities>"
|
||||||
)
|
)
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
|
||||||
|
@ -45,7 +47,7 @@ fn escape_back() {
|
||||||
|
|
||||||
// Owned
|
// Owned
|
||||||
let escape_back = from_str::<StructSpecialEntities>(
|
let escape_back = from_str::<StructSpecialEntities>(
|
||||||
"<StructSpecialEntities xmlns=\"URI\"><string><>&"'adsad"</string><str>str</str><cow>str&</cow></StructSpecialEntities>"
|
"<StructSpecialEntities xmlns=\"URI\"><string><>&"'adsad"</string><str>str</str><cow>str&</cow><list xmlns=\"\"><element xmlns=\"\">one</element><element xmlns=\"\">two</element><element xmlns=\"\">three</element></list></StructSpecialEntities>"
|
||||||
)
|
)
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
|
||||||
|
@ -61,7 +63,8 @@ fn special_entities() {
|
||||||
string: "&\"<>\'aa".to_string(),
|
string: "&\"<>\'aa".to_string(),
|
||||||
str: "&\"<>\'bb",
|
str: "&\"<>\'bb",
|
||||||
cow: Cow::from("&\"<>\'cc"),
|
cow: Cow::from("&\"<>\'cc"),
|
||||||
|
vec: vec!["one".into(), "two".into(), "three".into()]
|
||||||
}).unwrap(),
|
}).unwrap(),
|
||||||
"<StructSpecialEntities xmlns=\"URI\"><string>&"<>'aa</string><str>&"<>'bb</str><cow>&"<>'cc</cow></StructSpecialEntities>",
|
"<StructSpecialEntities xmlns=\"URI\"><string>&"<>'aa</string><str>&"<>'bb</str><cow>&"<>'cc</cow><list xmlns=\"\"><element xmlns=\"\">one</element><element xmlns=\"\">two</element><element xmlns=\"\">three</element></list></StructSpecialEntities>",
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue