Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

FromField should warn or error if #[darling(attributes(...))] and #[darling(forward_attrs(...))] are both empty #166

Open
Mingun opened this issue Mar 23, 2022 · 1 comment

Comments

@Mingun
Copy link

Mingun commented Mar 23, 2022

In #165 I faced with the problem, when I derive FromField for my struct and try to use it, but I've got nothing, because I've not specify #[darling(attributes(xml))]. Another derive that I tried before (if I remember correctly, FromAttributes) issues a compiler error about missing #[darling(attributes(...))].

It seems that without this attributes derive is useless, so it should be a compiler error if it is missed:

use darling::FromField;
use syn::{parse_macro_input, Data, DeriveInput, Fields};
use proc_macro::TokenStream;
use quote::ToTokens;

#[derive(Debug, Default, FromField)]
#[darling(default)]
//#[darling(attributes(xml))] // <<------------------------- missed 
struct FieldProps {
  /// Should be `true` when `#[xml(attribute)]` is present on a field and false otherwise:
  ///
  /// ```rust
  /// // ---> true
  /// #[xml(attribute)]
  /// field1: (),
  ///
  /// // ---> false
  /// field2: (),
  /// ```
  attribute: bool,
  // other attributes...
}

#[proc_macro_attribute]
pub fn quick_xml(_attr: TokenStream, item: TokenStream) -> TokenStream {
  let ast = parse_macro_input!(item as DeriveInput);

  if let Data::Struct(s) = &ast.data {
    if let Fields::Named(fields) = &s.fields {
      for f in &fields.named {
        let props = FieldProps::from_field(&f);

        println!("{}: {:?}", f.ident, props);
      }
    }
  }

  ast.into_token_stream().into()
}

successfully compiled

@TedDriggs
Copy link
Owner

Good catch! Technically, doing this works, it's just not very helpful with FromField.

Deriving FromDeriveInput and not passing attributes is actually useful, since you could use darling(supports(...)) for shape validation and the data field for automatic field conversion even if you don't care about any attributes - when I first built FromField I decided to allow it for consistency with FromDeriveInput. Now, however... I think it's reasonable to make it a compile error if both #[darling(attributes(...))] and #[darling(forward_attrs(...))] are empty.

P.S. If you didn't know about the FromDeriveInput trick, you can do the following:

#[derive(FromDeriveInput)]
#[darling(supports(struct_named))]
struct QuickXml {
    data: darling::ast::Data<(), FieldProps>
}

That would let you skip the if let pyramid in this example.

@TedDriggs TedDriggs changed the title FromField silently compiles without #[darling(attributes(...))] FromField should warn or error if #[darling(attributes(...))] and #[darling(forward_attrs(...))] are both empty Mar 23, 2022
TedDriggs added a commit that referenced this issue Apr 13, 2022
While FromDeriveInput is still useful without attribute parsing, FromField is of very limited utility.
Therefore, its use suggests the caller may have omitted the meta item.

Fixes #166
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants