2012-05-23 7 views
14

Ho un problema con l'annotazione @Valid di JSR-303. I annotation funziona bene per le liste o gruppi e normale, ma sto cercando di convalidare mappe che contengono liste, vale a direCome convalidare le raccolte in Maps

@Valid 
HashMap<String, ArrayList<Object1>> map; 

In questo caso, le istanze di Object1 classe non vengono convalidati. C'è un modo conveniente per farlo in modo ricorsivo, senza iterare su ogni oggetto e convalidarlo manualmente?

risposta

13

La specifica non specifica il comportamento di convalida quando i valori della mappa sono elenchi.

Da JSR 303 specification:

Ogni oggetto fornito dal iteratore viene convalidato. Per Mappa, il valore di ogni Map.Entry è convalidato (la chiave non è convalidata).

Poiché il valore nel tuo caso è un elenco, che non ha un'annotazione @Valid, non viene elaborato. Per ovviare a questo è possibile:

Avvolgere l'elenco contenuto in un altro bean, forzando l'elaborazione dell'annotazione nell'elenco.

public class ListHolder<T extends Iterable> { 
    @Valid 
    public T wrappedList; 
} 

Oppure, in alternativa è possibile scrivere una custom validator per gestire le mappe complesse. Qualcosa del genere:

@Target({ METHOD, FIELD, ANNOTATION_TYPE }) 
@Retention(RUNTIME) 
@Documented 
@Constraint(validatedBy = ValidMapValidator.class) 
public @interface ValidMap { 
    String message() default "valid.map"; 

    Class<?>[] groups() default {}; 

    Class<? extends Payload>[] payload() default {}; 
} 

public class ValidMapValidator implements 
     ConstraintValidator<ValidMap, Map<?, ?>> { 

    @Override 
    public void initialize(final ValidMap annotation) { 
     return; 
    } 

    @Override 
    public boolean isValid(final Map<?, ?> map, 
     final ConstraintValidatorContext context) { 
     if (map == null || map.size() == 0) 
     return true; 

     // Iterate each map entry and validate 
     return true; 
    } 
} 
+0

Sì, ho provato a scrivere un validatore personalizzato, ma per valutare l'oggetto reale ho bisogno di conoscere il tipo. Impostare > constraintViolations = validator.validate (car); – liecno

+0

È possibile utilizzare i caratteri jolly per il tipo generico. Vedi le modifiche alla mia risposta per un esempio su come impostare il validatore. – Perception