dashxhq / sanitizer

Dead easy sanitizing for rust structs
MIT License
10 stars 3 forks source link

Conflict with the validator crate derive macro #16

Open matous-volf opened 3 weeks ago

matous-volf commented 3 weeks ago

This does work:

use sanitizer::{StringSanitizer};
use sanitizer::prelude::Sanitize;
use validator::Validate;

#[derive(Sanitize)]
struct User {
    #[sanitize]
    pub kind: UserKind,
}

enum UserKind {
    Anonymous,
    SignedIn(String),
}

impl sanitizer::Sanitize for UserKind {
    fn sanitize(&mut self) {
        if let UserKind::SignedIn(s) = self {
            let mut sanitize = StringSanitizer::from(s.as_str());
            sanitize.trim();
            *s = sanitize.get();
        }
    }
}

fn main() {
    let mut user = User {
        kind: UserKind::SignedIn(" John  ".to_string()),
    };

    user.sanitize();

    if let UserKind::SignedIn(s) = user.kind {
        assert_eq!(s, "John");
    } else {
        panic!();
    }
}

However, after deriving from validator's Validate:

#[derive(Sanitize, Validate)]
struct User {
    #[sanitize]
    pub kind: UserKind,
}

I get

error: You need to set at least one validator on field `kind`

         = note: If you want nested validation, use `#[validate(nested)]`

 --> src/main.rs:7:5
  |
7 |     #[sanitize]
  |     ^

This, I suppose, should not happen. Either way, even when following the instruction:

[derive(Sanitize, Validate)]
struct User {
    #[sanitize]
    #[validate(nested)]
    pub kind: UserKind,
}

impl Validate for UserKind {
    fn validate(&self) -> Result<(), ValidationErrors> {
        Ok(())
    }
}

the error persists.

Maybe the issue is on the validator's side – I have no idea how derive macros work. Thanks in advance.

RabidFire commented 3 weeks ago

@matous-volf I think validate(nested) is meant for struct and not enum. What are you trying to achieve?

matous-volf commented 3 weeks ago

@RabidFire I would like to both sanitize and validate a struct, for instance the User. So my goal is basically:

#[derive(Sanitize, Validate)]
struct User {
    #[sanitize]
    pub kind: UserKind,
    #[validate(range(min = 18))]
    pub age: u32,
    ... other fields to sanitize and validate
}

But that won't compile, as shown above.

I don't necessarily need to validate the enum field (here kind), I just need to sanitize it. If I understand correctly, that should be possible because UserKind implements sanitizer::Sanitize.