Skip to content

Commit f6a4f6f

Browse files
committed
Don't panic on unions in darling_core
1 parent 2922dd5 commit f6a4f6f

File tree

8 files changed

+27
-13
lines changed

8 files changed

+27
-13
lines changed

core/src/ast/data.rs

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,20 @@ impl<V, F> Data<V, F> {
3131
}
3232
}
3333

34+
/// Creates an empty body of the same shape as the passed-in body.
35+
///
36+
/// `darling` does not support unions; calling this function with a union body will return an error.
37+
pub fn try_empty_from(src: &syn::Data) -> Result<Self> {
38+
match *src {
39+
syn::Data::Enum(_) => Ok(Data::Enum(vec![])),
40+
syn::Data::Struct(ref vd) => Ok(Data::Struct(Fields::empty_from(&vd.fields))),
41+
// This deliberately doesn't set a span on the error message, as the error is most useful if
42+
// applied to the call site of the offending macro. Given that the message is very generic,
43+
// putting it on the union keyword ends up being confusing.
44+
syn::Data::Union(_) => Err(Error::custom("Unions are not supported")),
45+
}
46+
}
47+
3448
/// Creates a new `Data<&'a V, &'a F>` instance from `Data<V, F>`.
3549
pub fn as_ref<'a>(&'a self) -> Data<&'a V, &'a F> {
3650
match *self {

core/src/options/core.rs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -41,11 +41,11 @@ pub struct Core {
4141

4242
impl Core {
4343
/// Partially initializes `Core` by reading the identity, generics, and body shape.
44-
pub fn start(di: &syn::DeriveInput) -> Self {
45-
Core {
44+
pub fn start(di: &syn::DeriveInput) -> Result<Self> {
45+
Ok(Core {
4646
ident: di.ident.clone(),
4747
generics: di.generics.clone(),
48-
data: Data::empty_from(&di.data),
48+
data: Data::try_empty_from(&di.data)?,
4949
default: Default::default(),
5050
// See https://github.com/TedDriggs/darling/issues/10: We default to snake_case
5151
// for enums to help authors produce more idiomatic APIs.
@@ -57,7 +57,7 @@ impl Core {
5757
map: Default::default(),
5858
bound: Default::default(),
5959
allow_unknown_fields: Default::default(),
60-
}
60+
})
6161
}
6262

6363
fn as_codegen_default<'a>(&'a self) -> Option<codegen::DefaultExpression<'a>> {

core/src/options/from_derive.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ pub struct FdiOptions {
2424
impl FdiOptions {
2525
pub fn new(di: &syn::DeriveInput) -> Result<Self> {
2626
(FdiOptions {
27-
base: OuterFrom::start(di),
27+
base: OuterFrom::start(di)?,
2828
vis: Default::default(),
2929
generics: Default::default(),
3030
data: Default::default(),

core/src/options/from_field.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@ pub struct FromFieldOptions {
1616
impl FromFieldOptions {
1717
pub fn new(di: &syn::DeriveInput) -> Result<Self> {
1818
(FromFieldOptions {
19-
base: OuterFrom::start(di),
19+
base: OuterFrom::start(di)?,
2020
vis: Default::default(),
2121
ty: Default::default(),
2222
})

core/src/options/from_meta.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ pub struct FromMetaOptions {
1313
impl FromMetaOptions {
1414
pub fn new(di: &syn::DeriveInput) -> Result<Self> {
1515
(FromMetaOptions {
16-
base: Core::start(di),
16+
base: Core::start(di)?,
1717
})
1818
.parse_attributes(&di.attrs)?
1919
.parse_body(&di.data)

core/src/options/from_type_param.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@ pub struct FromTypeParamOptions {
1616
impl FromTypeParamOptions {
1717
pub fn new(di: &syn::DeriveInput) -> Result<Self> {
1818
(FromTypeParamOptions {
19-
base: OuterFrom::start(di),
19+
base: OuterFrom::start(di)?,
2020
bounds: None,
2121
default: None,
2222
})

core/src/options/from_variant.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@ pub struct FromVariantOptions {
1919
impl FromVariantOptions {
2020
pub fn new(di: &DeriveInput) -> Result<Self> {
2121
(FromVariantOptions {
22-
base: OuterFrom::start(di),
22+
base: OuterFrom::start(di)?,
2323
discriminant: Default::default(),
2424
fields: Default::default(),
2525
supports: Default::default(),

core/src/options/outer_from.rs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -28,15 +28,15 @@ pub struct OuterFrom {
2828
}
2929

3030
impl OuterFrom {
31-
pub fn start(di: &syn::DeriveInput) -> Self {
32-
OuterFrom {
33-
container: Core::start(di),
31+
pub fn start(di: &syn::DeriveInput) -> Result<Self> {
32+
Ok(OuterFrom {
33+
container: Core::start(di)?,
3434
attrs: Default::default(),
3535
ident: Default::default(),
3636
attr_names: Default::default(),
3737
forward_attrs: Default::default(),
3838
from_ident: Default::default(),
39-
}
39+
})
4040
}
4141
}
4242

0 commit comments

Comments
 (0)