Improve error messages related to transparent

This commit is contained in:
David Tolnay
2018-05-20 15:09:51 -07:00
parent 1335f85213
commit ac1b25e91d
6 changed files with 74 additions and 71 deletions
+3 -31
View File
@@ -15,7 +15,7 @@ use syn::{self, Ident, Index, Member};
use bound;
use fragment::{Expr, Fragment, Match, Stmts};
use internals::ast::{Container, Data, Field, Style, Variant};
use internals::{attr, Ctxt};
use internals::{attr, Ctxt, Derive};
use pretend;
use try;
@@ -23,7 +23,7 @@ use std::collections::BTreeSet;
pub fn expand_derive_deserialize(input: &syn::DeriveInput) -> Result<TokenStream, String> {
let ctxt = Ctxt::new();
let cont = Container::from_ast(&ctxt, input);
let cont = Container::from_ast(&ctxt, input, Derive::Deserialize);
precondition(&ctxt, &cont);
try!(ctxt.check());
@@ -355,7 +355,7 @@ fn deserialize_transparent(cont: &Container, params: &Parameters) -> Fragment {
};
let this = &params.this;
let transparent_field = find_transparent_field(fields);
let transparent_field = fields.iter().find(|f| f.attrs.transparent()).unwrap();
let path = match transparent_field.attrs.deserialize_with() {
Some(path) => quote!(#path),
@@ -383,34 +383,6 @@ fn deserialize_transparent(cont: &Container, params: &Parameters) -> Fragment {
}
}
fn find_transparent_field<'a>(fields: &'a [Field<'a>]) -> &'a Field<'a> {
let mut transparent_field = None;
for field in fields {
if field.attrs.skip_deserializing() {
continue;
}
if field.attrs.default().is_none() {
if let syn::Type::Path(ref ty) = field.ty {
if let Some(seg) = ty.path.segments.last() {
if seg.into_value().ident == "PhantomData" {
continue;
}
}
}
if transparent_field.is_some() {
panic!("Ambiguous transparent field");
}
transparent_field = Some(field);
}
}
match transparent_field {
Some(transparent_field) => transparent_field,
None => panic!("No field can be transparent"),
}
}
fn deserialize_from(type_from: &syn::Type) -> Fragment {
quote_block! {
_serde::export::Result::map(