quinta-feira, 14 de junho de 2012

JSR 303 + Hibernate Validator + Spring Parte 2

JSR 303 Bean validator e Hibernate validator Parte 1

Como visto no post anterior utilizar bean validador não é nenhum grande mistério, agora chega de console e vou mostrar como utilizar em algo mais concreto, como um formulario HTML e Spring.

Recomendo que já conheça o basico do Spring, pois não vou entrar nos detalhes do framework, apenas na parte de validação

Dependencias
Spring
Hibernate validator 


Vamos começar criando a entidade como no post anterior

package br.com.cristiano;

import javax.validation.constraints.NotNull;
import javax.validation.constraints.Size;

import org.hibernate.validator.constraints.Email;

public class Cliente {

 private String nome;
 private String email;
 
 @Size(min=5, message="Nome deve ter mais que 5 caracteres")
 @NotNull(message="Nome não pode ser nulo")
 public String getNome() {
  return nome;
 }
 public void setNome(String nome) {
  this.nome = nome;
 }
 
 @Email(message="Email invalido")
 public String getEmail() {
  return email;
 }
 public void setEmail(String email) {
  this.email = email;
 }
 
}


Até ai nada como, isso já foi mostrado e explicado no post anterior, agora vamos para a parte do Spring criando o Controller
package br.com.cristiano;

import javax.validation.Valid;

import org.springframework.stereotype.Controller;
import org.springframework.validation.BindingResult;
import org.springframework.web.bind.annotation.RequestMapping;

@Controller
public class ClienteController {

 @RequestMapping("formulario")
 public String form(){
  return "formulario";
 }
 
 @RequestMapping("adicionaCliente")
 public String adicionar(@Valid Cliente cliente, BindingResult result){
  if(result.hasErrors()){
   return "formulario";
  }
  return "adicionada";
 }
}

Note que o metodo recebe um anotação @Valid que vai validar a classe anotada e o parametro do tipo BidingResults tem uma grande quantidade de metodos que se referem ao registro de erros no form como, se tem erro ou não na resposta, quem deu erro, quantidade de erros, etc

Agora vou demonstrar como mostrar o(s) erro(s) no form.
O próprio Spring tem uma taglib para isso

<%@taglib uri="http://www.springframework.org/tags/form" prefix="form"%>
crie uma pagina jsp com o nome formulario.jsp

<%@ page language="java" contentType="text/html; charset=ISO-8859-1"
 pageEncoding="ISO-8859-1"%>

<%@taglib uri="http://www.springframework.org/tags/form" prefix="form"%>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=ISO-8859-1">
<title>Adicionar cliente</title>
</head>
<body>
   <form action="adicionaCliente" method="post">
      Nome:
        
      <form:errors cssstyle="color:red;" path="cliente.nome">
      <br />
      Email:
      
      <form:errors cssstyle="color:red;" path="cliente.email">
      <br />
      
   </form>
</body>
</html>
Estrutura do projeto

Github: https://github.com/cristianoperez/SpringValidator

quinta-feira, 3 de maio de 2012

JSR 303 Bean validator e Hibernate validator Parte 1

Digamos que você gostaria de validar um dado que o usuario digitou, validar um CPF se o campo é nulo, você pode fazer no inicio do metodo algo como

if(cliente.cnpj == null, cliente.nome == null){
   throw new Exception("Preencha os campos obrigatórios");
}

Ira funcionar? Sim, ou talvez não do jeito que você planejou, e se eu quiser saber se o cnpj tem o tamanho exato, ou se ele é valido, pois podem existir outra dezenas de validações para um campo e imagina o trabalho que iria dar colocar todas a validações todas as vezes em cada metodo, não iríamos criar um metodo e sim um monstro.
Para simplificar isso foi criado e aprovado o JSR 303 ou Bean validator.

Bean validator também conhecido como JSR 303 foi uma especificação aprovada no final de 2009 pela JCP (Java community process) e faz parte do JavaEE 6, segundo a propria especificação ela faz o seguinte.

CUIDADO CONTEUDO ALTAMENTE TEÓRICO

“This JSR defines a metadata model and API for JavaBean validation. The default metadata source is annotations, with the ability to override and extend the meta-data through the use of XML validation descriptors.
The validation API developed by this JSR is not intended for use in any one tier or programming model. It is specifically not tied to either the web tier or the persistence tier, and is available for both server-side application programming, as well as rich client Swing application developers.” – JSR-303 Specification

Tradução livre feita pelo autor

Essa JSR define um modelo de matadados e API para validar o JavaBean. O matadado padrão é a anotação, tem que a habilidade de sobrescrever e estender o metadado através do uso de validação XML.
A API de validação desenvolvida por essa JRS não tem a intenção de uso em nenhuma camada ou modelo de programação. Ela não esta atrelada a nenhuma camada web ou camada de persistencia, e esta disponível tanto para aplicação do lado servidor como para desenvolvedores que utilizam Swing.

Agora você me pergunta ótimo mais como eu faço para usar essa tal de jsr 303, quero validar meus campos. Para isso você não ira precisar ficar criando validações uma a uma, ja existe implementações dessa JSR, o mais famoso e utilizado e o Hibernate validator, para utilizá-lo basta baixar o arquivo e utilizar os seguintes jars

Hibernate-validator-xxx.jar
Validation-api-xxx.jar
Jboss-logging-xxx.jar

Com isso você já esta pronto para utilizar o bean validator.
Crie uma classe chamada Cliente com os seguintes campos id, nome, email e em cima delas utilizar a anotação @NotNull @Size @Email todas do pacote.

public class Cliente {

@NotNull(message="Valor não pode ser nulo")
private Integer id;

@Size(min=5, message="Tamanho deve ser maior que 5")
@NotNull(message="Nome não pode ser nulo")
private String nome;

@Email(message="Email invalido")
private String email;

//getters and setters

}

Note que para todas as anotações existe um atributo chamado message, que é a mensagem que sera passada caso o campo não seja validado.
Agora vamos criar um cliente console para mostrar a validação em funcionamento.


public class Client {

 public static void main(String[] args) {
  //Nome menor que 5, email invalido
  Cliente cliente = new Cliente(1, "Cris", "adminqwdadmin.com");
  
  ValidatorFactory factory = Validation.buildDefaultValidatorFactory();
        Validator validator = factory.getValidator();
  Set<constraintviolation<Cliente> constraintViolations = validator.validate(cliente);
  for(ConstraintViolation error : constraintViolations){
   System.out.println(error.getMessage());
  }
 }
}

Retorno no console


É isso, espero que tenham gostado, essa foi apenas a primeira parte sobre Hibernate validator, o proximo post sera como integralo com Spring e utilizado em um formulario HTML.


Parte 2