Add support for elements in unnamed fields
This commit is contained in:
parent
c24d2cdaac
commit
72b8a21b4d
|
@ -249,7 +249,7 @@ fn deserialize_struct(
|
|||
into: &mut Option<Self>,
|
||||
) -> Result<(), ::instant_xml::Error> {
|
||||
use ::instant_xml::de::Node;
|
||||
use ::instant_xml::{Error, Id};
|
||||
use ::instant_xml::{Error, Id, Kind};
|
||||
|
||||
enum __Elements {
|
||||
#elements_enum
|
||||
|
@ -353,9 +353,16 @@ fn named_field(
|
|||
|
||||
if !field_meta.attribute {
|
||||
tokens.r#match.extend(quote!(
|
||||
__Elements::#enum_name => {
|
||||
let mut nested = deserializer.nested(data);
|
||||
<#no_lifetime_type>::deserialize(&mut nested, &mut #enum_name)?;
|
||||
__Elements::#enum_name => match <#no_lifetime_type as FromXml>::KIND {
|
||||
Kind::Element(_) => {
|
||||
let mut nested = deserializer.nested(data);
|
||||
FromXml::deserialize(&mut nested, &mut #enum_name)?;
|
||||
}
|
||||
Kind::Scalar => {
|
||||
let mut nested = deserializer.nested(data);
|
||||
FromXml::deserialize(&mut nested, &mut #enum_name)?;
|
||||
nested.ignore()?;
|
||||
}
|
||||
},
|
||||
));
|
||||
} else {
|
||||
|
@ -418,7 +425,7 @@ fn deserialize_tuple_struct(
|
|||
into: &mut Option<Self>,
|
||||
) -> Result<(), ::instant_xml::Error> {
|
||||
use ::instant_xml::de::Node;
|
||||
use ::instant_xml::{Error, Id};
|
||||
use ::instant_xml::{Error, Id, Kind};
|
||||
|
||||
#declare_values
|
||||
|
||||
|
@ -446,25 +453,24 @@ fn unnamed_field(
|
|||
|
||||
let name = Ident::new(&format!("v{index}"), Span::call_site());
|
||||
declare_values.extend(quote!(
|
||||
let node = match deserializer.next() {
|
||||
Some(result) => result?,
|
||||
None => return Err(Error::MissingValue(&<#no_lifetime_type as FromXml>::KIND)),
|
||||
};
|
||||
|
||||
let #name = match node {
|
||||
Node::Open(data) => {
|
||||
let mut nested = deserializer.nested(data);
|
||||
let #name = match <#no_lifetime_type as FromXml>::KIND {
|
||||
Kind::Element(_) => match deserializer.next() {
|
||||
Some(Ok(Node::Open(data))) => {
|
||||
let mut nested = deserializer.nested(data);
|
||||
let mut value: Option<#no_lifetime_type> = None;
|
||||
<#no_lifetime_type>::deserialize(&mut nested, &mut value)?;
|
||||
value
|
||||
}
|
||||
Some(Ok(node)) => return Err(Error::UnexpectedNode(format!("{:?}", node))),
|
||||
Some(Err(e)) => return Err(e),
|
||||
None => return Err(Error::MissingValue(&<#no_lifetime_type as FromXml>::KIND)),
|
||||
}
|
||||
Kind::Scalar => {
|
||||
let mut nested = deserializer.for_scalar();
|
||||
let mut value: Option<#no_lifetime_type> = None;
|
||||
<#no_lifetime_type>::deserialize(&mut nested, &mut value)?;
|
||||
value
|
||||
}
|
||||
Node::Text(data) => {
|
||||
let mut nested = deserializer.for_node(Node::Text(data));
|
||||
let mut value: Option<#no_lifetime_type> = None;
|
||||
<#no_lifetime_type>::deserialize(&mut nested, &mut value)?;
|
||||
value
|
||||
}
|
||||
node => return Err(Error::UnexpectedNode(format!("{:?}", node))),
|
||||
};
|
||||
));
|
||||
|
||||
|
|
|
@ -29,27 +29,13 @@ impl<'cx, 'xml> Deserializer<'cx, 'xml> {
|
|||
}
|
||||
|
||||
pub fn take_str(&mut self) -> Result<&'xml str, Error> {
|
||||
let (value, element) = match self.next() {
|
||||
Some(Ok(Node::AttributeValue(s))) => (s, false),
|
||||
Some(Ok(Node::Text(s))) => (s, true),
|
||||
match self.next() {
|
||||
Some(Ok(Node::AttributeValue(s))) => Ok(s),
|
||||
Some(Ok(Node::Text(s))) => Ok(s),
|
||||
Some(Ok(_)) => return Err(Error::ExpectedScalar),
|
||||
Some(Err(e)) => return Err(e),
|
||||
None => return Err(Error::MissingValue(&Kind::Scalar)),
|
||||
};
|
||||
|
||||
if element {
|
||||
match self.next() {
|
||||
Some(Ok(_)) => {
|
||||
return Err(Error::UnexpectedState(
|
||||
"found element while expecting scalar",
|
||||
))
|
||||
}
|
||||
Some(Err(e)) => return Err(e),
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
|
||||
Ok(value)
|
||||
}
|
||||
|
||||
pub fn nested<'a>(&'a mut self, element: Element<'xml>) -> Deserializer<'a, 'xml>
|
||||
|
@ -73,6 +59,19 @@ impl<'cx, 'xml> Deserializer<'cx, 'xml> {
|
|||
}
|
||||
}
|
||||
|
||||
pub fn for_scalar<'a>(&'a mut self) -> Deserializer<'a, 'xml>
|
||||
where
|
||||
'cx: 'a,
|
||||
{
|
||||
Deserializer {
|
||||
local: self.local,
|
||||
prefix: self.prefix,
|
||||
level: self.level,
|
||||
done: self.done,
|
||||
context: self.context,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn for_node<'a>(&'a mut self, node: Node<'xml>) -> Deserializer<'a, 'xml>
|
||||
where
|
||||
'cx: 'a,
|
||||
|
|
|
@ -10,3 +10,28 @@ fn one_number() {
|
|||
assert_eq!(xml, to_string(&v).unwrap());
|
||||
assert_eq!(v, from_str(xml).unwrap());
|
||||
}
|
||||
|
||||
#[derive(Debug, Eq, FromXml, PartialEq, ToXml)]
|
||||
struct OneString(String);
|
||||
|
||||
#[test]
|
||||
fn one_string() {
|
||||
let v = OneString("f42".to_owned());
|
||||
let xml = r#"<OneString>f42</OneString>"#;
|
||||
assert_eq!(xml, to_string(&v).unwrap());
|
||||
assert_eq!(v, from_str(xml).unwrap());
|
||||
}
|
||||
|
||||
#[derive(Debug, Eq, FromXml, PartialEq, ToXml)]
|
||||
struct StringElement(String, Foo);
|
||||
|
||||
#[derive(Debug, Eq, FromXml, PartialEq, ToXml)]
|
||||
struct Foo;
|
||||
|
||||
#[test]
|
||||
fn string_element() {
|
||||
let v = StringElement("f42".to_owned(), Foo);
|
||||
let xml = r#"<StringElement>f42<Foo></Foo></StringElement>"#;
|
||||
assert_eq!(xml, to_string(&v).unwrap());
|
||||
assert_eq!(v, from_str(xml).unwrap());
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue