Merge pull request #1022 from sfackler/skip-field
Inform serializers about skipped fields.
This commit is contained in:
commit
800620e2aa
@ -1727,6 +1727,13 @@ pub trait SerializeStruct {
|
|||||||
where
|
where
|
||||||
T: Serialize;
|
T: Serialize;
|
||||||
|
|
||||||
|
/// Indicate that a struct field has been skipped.
|
||||||
|
#[inline]
|
||||||
|
fn skip_field(&mut self, key: &'static str) -> Result<(), Self::Error> {
|
||||||
|
let _ = key;
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
/// Finish serializing a struct.
|
/// Finish serializing a struct.
|
||||||
fn end(self) -> Result<Self::Ok, Self::Error>;
|
fn end(self) -> Result<Self::Ok, Self::Error>;
|
||||||
}
|
}
|
||||||
@ -1772,6 +1779,13 @@ pub trait SerializeStructVariant {
|
|||||||
where
|
where
|
||||||
T: Serialize;
|
T: Serialize;
|
||||||
|
|
||||||
|
/// Indicate that a struct variant field has been skipped.
|
||||||
|
#[inline]
|
||||||
|
fn skip_field(&mut self, key: &'static str) -> Result<(), Self::Error> {
|
||||||
|
let _ = key;
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
/// Finish serializing a struct variant.
|
/// Finish serializing a struct variant.
|
||||||
fn end(self) -> Result<Self::Ok, Self::Error>;
|
fn end(self) -> Result<Self::Ok, Self::Error>;
|
||||||
}
|
}
|
||||||
|
@ -1384,9 +1384,14 @@ fn deserialize_identifier(
|
|||||||
"field identifier"
|
"field identifier"
|
||||||
};
|
};
|
||||||
|
|
||||||
let visit_index = if is_variant {
|
let index_expecting = if is_variant {
|
||||||
|
"variant"
|
||||||
|
} else {
|
||||||
|
"field"
|
||||||
|
};
|
||||||
|
|
||||||
let variant_indices = 0u32..;
|
let variant_indices = 0u32..;
|
||||||
let fallthrough_msg = format!("variant index 0 <= i < {}", fields.len());
|
let fallthrough_msg = format!("{} index 0 <= i < {}", index_expecting, fields.len());
|
||||||
let visit_index = quote! {
|
let visit_index = quote! {
|
||||||
fn visit_u32<__E>(self, __value: u32) -> _serde::export::Result<Self::Value, __E>
|
fn visit_u32<__E>(self, __value: u32) -> _serde::export::Result<Self::Value, __E>
|
||||||
where __E: _serde::de::Error
|
where __E: _serde::de::Error
|
||||||
@ -1401,10 +1406,6 @@ fn deserialize_identifier(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
Some(visit_index)
|
|
||||||
} else {
|
|
||||||
None
|
|
||||||
};
|
|
||||||
|
|
||||||
let bytes_to_str = if fallthrough.is_some() {
|
let bytes_to_str = if fallthrough.is_some() {
|
||||||
None
|
None
|
||||||
|
@ -242,6 +242,7 @@ fn serialize_struct(params: &Parameters, fields: &[Field], cattrs: &attr::Contai
|
|||||||
params,
|
params,
|
||||||
false,
|
false,
|
||||||
quote!(_serde::ser::SerializeStruct::serialize_field),
|
quote!(_serde::ser::SerializeStruct::serialize_field),
|
||||||
|
quote!(_serde::ser::SerializeStruct::skip_field),
|
||||||
);
|
);
|
||||||
|
|
||||||
let type_name = cattrs.name().serialize_name();
|
let type_name = cattrs.name().serialize_name();
|
||||||
@ -707,15 +708,23 @@ fn serialize_struct_variant<'a>(
|
|||||||
fields: &[Field],
|
fields: &[Field],
|
||||||
name: &str,
|
name: &str,
|
||||||
) -> Fragment {
|
) -> Fragment {
|
||||||
let method = match context {
|
let (method, skip_method) = match context {
|
||||||
StructVariant::ExternallyTagged { .. } => {
|
StructVariant::ExternallyTagged { .. } => {
|
||||||
quote!(_serde::ser::SerializeStructVariant::serialize_field)
|
(
|
||||||
|
quote!(_serde::ser::SerializeStructVariant::serialize_field),
|
||||||
|
quote!(_serde::ser::SerializeStructVariant::skip_field),
|
||||||
|
)
|
||||||
}
|
}
|
||||||
StructVariant::InternallyTagged { .. } |
|
StructVariant::InternallyTagged { .. } |
|
||||||
StructVariant::Untagged => quote!(_serde::ser::SerializeStruct::serialize_field),
|
StructVariant::Untagged => {
|
||||||
|
(
|
||||||
|
quote!(_serde::ser::SerializeStruct::serialize_field),
|
||||||
|
quote!(_serde::ser::SerializeStruct::skip_field),
|
||||||
|
)
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
let serialize_fields = serialize_struct_visitor(fields, params, true, method);
|
let serialize_fields = serialize_struct_visitor(fields, params, true, method, skip_method);
|
||||||
|
|
||||||
let mut serialized_fields = fields
|
let mut serialized_fields = fields
|
||||||
.iter()
|
.iter()
|
||||||
@ -829,6 +838,7 @@ fn serialize_struct_visitor(
|
|||||||
params: &Parameters,
|
params: &Parameters,
|
||||||
is_enum: bool,
|
is_enum: bool,
|
||||||
func: Tokens,
|
func: Tokens,
|
||||||
|
skip_func: Tokens,
|
||||||
) -> Vec<Tokens> {
|
) -> Vec<Tokens> {
|
||||||
fields
|
fields
|
||||||
.iter()
|
.iter()
|
||||||
@ -859,7 +869,15 @@ fn serialize_struct_visitor(
|
|||||||
|
|
||||||
match skip {
|
match skip {
|
||||||
None => ser,
|
None => ser,
|
||||||
Some(skip) => quote!(if !#skip { #ser }),
|
Some(skip) => {
|
||||||
|
quote! {
|
||||||
|
if !#skip {
|
||||||
|
#ser
|
||||||
|
} else {
|
||||||
|
try!(#skip_func(&mut __serde_state, #key_expr));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
)
|
)
|
||||||
|
@ -521,6 +521,15 @@ declare_tests! {
|
|||||||
Token::I32(2),
|
Token::I32(2),
|
||||||
Token::MapEnd,
|
Token::MapEnd,
|
||||||
],
|
],
|
||||||
|
Struct { a: 1, b: 2, c: 0 } => &[
|
||||||
|
Token::Map { len: Some(3) },
|
||||||
|
Token::U32(0),
|
||||||
|
Token::I32(1),
|
||||||
|
|
||||||
|
Token::U32(1),
|
||||||
|
Token::I32(2),
|
||||||
|
Token::MapEnd,
|
||||||
|
],
|
||||||
Struct { a: 1, b: 2, c: 0 } => &[
|
Struct { a: 1, b: 2, c: 0 } => &[
|
||||||
Token::Struct { name: "Struct", len: 3 },
|
Token::Struct { name: "Struct", len: 3 },
|
||||||
Token::Str("a"),
|
Token::Str("a"),
|
||||||
|
Loading…
x
Reference in New Issue
Block a user