From 055a654a3d7a0e6c4dfebee70d135342299a00d2 Mon Sep 17 00:00:00 2001 From: Dirkjan Ochtman Date: Mon, 21 Nov 2022 20:33:11 -0800 Subject: [PATCH] Add support for generic type arguments --- instant-xml-macros/src/lib.rs | 6 ++++++ instant-xml-macros/src/ser.rs | 9 ++++++++- instant-xml/tests/generics.rs | 26 ++++++++++++++++++++++++++ 3 files changed, 40 insertions(+), 1 deletion(-) create mode 100644 instant-xml/tests/generics.rs diff --git a/instant-xml-macros/src/lib.rs b/instant-xml-macros/src/lib.rs index e4eb3e4..b80662f 100644 --- a/instant-xml-macros/src/lib.rs +++ b/instant-xml-macros/src/lib.rs @@ -79,6 +79,12 @@ impl<'input> ContainerMeta<'input> { .extend(xml_generics.lifetimes().map(|lt| lt.lifetime.clone())); xml_generics.params.push(xml.into()); + for param in xml_generics.type_params_mut() { + param + .bounds + .push(syn::parse_str("::instant_xml::FromXml<'xml>").unwrap()); + } + xml_generics } diff --git a/instant-xml-macros/src/ser.rs b/instant-xml-macros/src/ser.rs index 3cc5d90..750d307 100644 --- a/instant-xml-macros/src/ser.rs +++ b/instant-xml-macros/src/ser.rs @@ -91,7 +91,14 @@ fn serialize_struct( )); } - let (impl_generics, ty_generics, where_clause) = input.generics.split_for_impl(); + let mut generics = input.generics.clone(); + for param in generics.type_params_mut() { + param + .bounds + .push(syn::parse_str("::instant_xml::ToXml").unwrap()); + } + + let (impl_generics, ty_generics, where_clause) = generics.split_for_impl(); let tag = meta.tag(); let ident = &input.ident; diff --git a/instant-xml/tests/generics.rs b/instant-xml/tests/generics.rs new file mode 100644 index 0000000..5664be4 --- /dev/null +++ b/instant-xml/tests/generics.rs @@ -0,0 +1,26 @@ +use instant_xml::{from_str, to_string, FromXml, ToXml}; + +#[derive(Debug, Eq, FromXml, ToXml, PartialEq)] +struct Foo { + inner: T, +} + +#[derive(Debug, Eq, FromXml, ToXml, PartialEq)] +struct Bar { + bar: String, +} + +#[allow(clippy::disallowed_names)] +#[test] +fn serialize_generics() { + let foo = Foo { + inner: Bar { + bar: "Bar".to_owned(), + }, + }; + + let xml = "Bar"; + + assert_eq!(to_string(&foo).unwrap(), xml); + assert_eq!(from_str::>(xml).unwrap(), foo); +}