La validación de los datos ingresados por un usuario es una tarea habitual en la mayoría de las aplicaciones web. Los invito a explorar una manera de realizar las validaciones en aplicaciones java.
Las validaciones pueden realizarse manualmente con una concatenación infinita de IFs (ufff!!!), o podemos aprovechar las facilidades que nos ofrece Hibernate Validator que es la implementación más conocida de la especificación Bean Validation.
Configuración con Spring Boot
Para aplicaciones web, spring-boot-starter-web
ya trae incluido Hibernate Validator.
Para aplicaciones no web usar spring-boot-starter-validation
.
Anotaciones de validación
Las validaciones se expresan por medio de anotaciones. Estas anotaciones se pueden utilizar a nivel de atributo de una clase. Veamos un ejemplo:
public class Cliente {
@Size(min=2, max=30)
private String nombre;
@NotEmpty @Email
private String email;
@NotNull @Min(18) @Max(100)
private Integer edad;
@NotNull @Past
private LocalDate fechaNacimiento;
List<@NotBlank String> preferencias;
}
Como estas anotaciones existen muchas más que podemos utilizar para validar los atributos de nuestra entidad.
Ejecución de la validaciones
La ejecución de la validación se puede hacer programáticamente o mediante anotaciones.
Programáticamente
public void crearCliente(Cliente cliente) {
ValidatorFactory factory = Validation.buildDefaultValidatorFactory();
Validator validator = factory.getValidator();
Set<ConstraintViolation<Cliente>> errores = validator.validate(cliente);
for (ConstraintViolation<Cliente> error : errores) {
... manejo de errores ...
}
if (errores.isEmpty()) {
... lógica para crear un cliente …
}
}
Con anotaciones
@Service
@Validated
public class ClienteService {
public void crearCliente(@Valid Cliente cliente) {
... lógica para crear un cliente ...
}
}
La anotación @Validated ejecuta validaciones para los métodos de una clase. Con @Valid se indican los parámetros que se quiere validar.
Si falla alguna validación, se lanza ConstraintViolationException, con una colección del tipo ConstraintViolation
Grupos de validación
Las validaciones se pueden agrupar, para ejecutar un determinado subconjunto de validaciones en distintos métodos. Las validaciones que no tienen un grupo definido, tienen asociado el grupo Default.class
Para crear un nuevo grupo se crea una interfaz con el nombre del grupo elegido:
public interface ValidacionCompleta {
}
Y usamos este nuevo grupo para el atributo email:
public class Cliente {
@Size(min=2, max=30)
private String nombre;
@NotEmpty @Email(groups = {ValidacionCompleta.class})
private String email;
@NotNull @Min(18) @Max(100)
private Integer edad;
@NotNull @Past
private LocalDate fechaNacimiento;
}
En el service definimos como utilizar los grupos dependiendo del método:
@Service
@Validated
public class ClienteService {
@Validated(Default.class)
public void crearCliente(@Valid Cliente cliente) {
... lógica para crear un cliente ...
}
@Validated(values = {Default.class, ValidacionCompleta.class})
public void crearClienteCompleto(@Valid Cliente cliente) {
... lógica para crear un cliente ...
}
}
Validaciones anidadas
Cuando tenemos atributos que son clases propias con validaciones, debemos anotarlos con @Valid:
public class Cliente {
@Size(min=2, max=30)
private String nombre;
@Valid
private Direccion direccion;
}
public class Direccion {
@NotEmpty
private String calle;
@NotNull
private Integer altura;
private Integer piso;
private String departamento;
}
Personalización de mensajes de error
Todas las anotaciones predefinidas tienen un mensaje de error por defecto. El idioma en que se muestra depende del que tenga configurada la JVM. Si se desea cambiar el idioma:
org.springframework.context.i18n.LocaleContextHolder.setLocale(new Locale("es"));
Se puede sobrescribir el atributo message con un mensaje propio:
@Min(value = 18, message = "La edad no debe ser menor a 18 años")
Conclusión
Las validaciones son una parte importante y recurrente de nuestras aplicaciones. Hacerlas menos verborrágicas facilitan el entendimiento y el mantenimiento de las mismas.
Con las anotaciones las entidades de dominio quedan autodocumentadas con respecto a la validación de sus atributos, y si las validaciones son necesarias en mas de un método, se pueden reutilizar con la facilidad de grupos de validación.
En el siguiente artículo de validaciones veremos como crear nuestras propias anotaciones de validación.
Hasta la próxima !!