Make a query with criteria hibernate with Spring

2

Good evening, friends, I have a question.

I have a Class called Proposal and another Call Client.

In the client there is the CPF field and a Proposal has a Client.

I need to search for proposta.cliente.cpf , but I can not, could you help me?

Proposed Model

@Entity @Table (name="proposal") // I will refer to the flyway // public class Proposal implements Serializable {

private static final long serialVersionUID = 1L;

// Relacionamento Proposta x Produto
@NotNull(message = "O produto é obrigatório")
@ManyToOne
@JoinColumn(name = "codigo_produto")
private Produto produto;

// Relacionamento Proposta x Banco
@NotNull(message = "O banco é obrigatório")
@ManyToOne
@JoinColumn(name = "codigo_banco")
private Banco banco;

@NotNull(message = "A tabela é obrigatório")
@ManyToOne
@JoinColumn(name = "codigo_tabela")
private Tabela tabela;

@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long codigo;

// Padrao de expressao
// @ADE
@NotBlank(message = "A ADE é obrigatória")
@Size(max = 50, message = "O tamanho da ADE deve estar entre 1 e 50")
@Column(unique = true)
private String ade;

@NotBlank(message = "A descrição é obrigatória")
@Size(max = 50, message = "O tamanho da  descrição deve estar entre 1 e 50")
private String descricao;

@NotNull(message = "A origem é obrigatório")
@Enumerated(EnumType.STRING)
private Origem origem;

@NotNull(message = "O valor Parcela é obrigatório")
@DecimalMin("0.01")
@DecimalMax(value = "9999999.99", message = "O valor da proposta deve ser menor que R$9.999.999,99")
private BigDecimal valorParcela;

@NotNull(message = "O valor Total é obrigatório")
@DecimalMin("0.01")
@DecimalMax(value = "9999999.99", message = "O valor da proposta deve ser menor que R$9.999.999,99")
private BigDecimal valorTotal;

@NotNull(message = "O valor Líquido é obrigatório")
@DecimalMin("0.01")
@DecimalMax(value = "9999999.99", message = "O valor da proposta deve ser menor que R$9.999.999,99")
private BigDecimal valorLiquido;

@Column(name = "data_proposta")
private LocalDate dataProposta;

@ManyToOne
@JoinColumn(name = "codigo_cliente")
private Cliente cliente;

@OneToMany(mappedBy = "proposta")
private List<Comissao> comissoes;

@PrePersist
@PreUpdate
private void prePersistUpdate() {
    descricao = descricao.toUpperCase();
}

public Produto getProduto() {
    return produto;
}

public void setProduto(Produto produto) {
    this.produto = produto;
}

public Banco getBanco() {
    return banco;
}

public void setBanco(Banco banco) {
    this.banco = banco;
}

public Tabela getTabela() {
    return tabela;
}

public void setTabela(Tabela tabela) {
    this.tabela = tabela;
}

public Long getCodigo() {
    return codigo;
}

public void setCodigo(Long codigo) {
    this.codigo = codigo;
}

public String getAde() {
    return ade;
}

public void setAde(String ade) {
    this.ade = ade;
}

public String getDescricao() {
    return descricao;
}

public void setDescricao(String descricao) {
    this.descricao = descricao;
}

public Origem getOrigem() {
    return origem;
}

public void setOrigem(Origem origem) {
    this.origem = origem;
}

public BigDecimal getValorParcela() {
    return valorParcela;
}

public void setValorParcela(BigDecimal valorParcela) {
    this.valorParcela = valorParcela;
}

public BigDecimal getValorTotal() {
    return valorTotal;
}

public void setValorTotal(BigDecimal valorTotal) {
    this.valorTotal = valorTotal;
}

public BigDecimal getValorLiquido() {
    return valorLiquido;
}

public void setValorLiquido(BigDecimal valorLiquido) {
    this.valorLiquido = valorLiquido;
}

public Cliente getCliente() {
    return cliente;
}

public void setCliente(Cliente cliente) {
    this.cliente = cliente;
}

public List<Comissao> getComissoes() {
    return comissoes;
}

public void setComissoes(List<Comissao> comissoes) {
    this.comissoes = comissoes;
}

public LocalDate getDataProposta() {
    return dataProposta;
}

public void setDataProposta(LocalDate dataProposta) {
    this.dataProposta = dataProposta;
}

@Override
public int hashCode() {
    final int prime = 31;
    int result = 1;
    result = prime * result + ((codigo == null) ? 0 : codigo.hashCode());
    return result;
}

@Override
public boolean equals(Object obj) {
    if (this == obj)
        return true;
    if (obj == null)
        return false;
    if (getClass() != obj.getClass())
        return false;
    Proposta other = (Proposta) obj;
    if (codigo == null) {
        if (other.codigo != null)
            return false;
    } else if (!codigo.equals(other.codigo))
        return false;
    return true;
}

public Proposta(Produto produto, Banco banco, Tabela tabela, Long codigo, String ade, String descricao,
        Origem origem, BigDecimal valorParcela, BigDecimal valorTotal, BigDecimal valorLiquido, Cliente cliente,
        List<Comissao> comissoes) {
    super();
    this.produto = produto;
    this.banco = banco;
    this.tabela = tabela;
    this.codigo = codigo;
    this.ade = ade;
    this.descricao = descricao;
    this.origem = origem;
    this.valorParcela = valorParcela;
    this.valorTotal = valorTotal;
    this.valorLiquido = valorLiquido;
    this.cliente = cliente;
    this.comissoes = comissoes;
}

public Proposta() {
    super();
}

}

Model Client

@Entity @Table (name="client") public class Client implements Serializable {

private static final long serialVersionUID = 1L;

@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(unique = true)
private Long codigo;

@NotBlank(message = "Nome é obrigatório")
@Size(max = 50, message = "O tamanho da  descrição deve estar entre 1 e 50")
private String nome;

@NotBlank(message = "Sobrenome obrigatório")
@Size(max = 50, message = "O tamanho da  descrição deve estar entre 1 e 50")
private String sobrenome;

@NotBlank(message = "Email é obrigatorio")
@Column(unique = true)
private String email;

@NotBlank(message = "Telefone é obrigatorio")
private String telefone;

@NotBlank(message = "CPF é obrigatório")
@Column(unique = true)
private String cpf;

@NotBlank(message = "CPF é obrigatório")
private String rg;

@OneToMany(mappedBy = "usuario")
private List<Equipe> equipes;

@Enumerated(EnumType.STRING)
private Genero genero;

@NotNull(message = "A conta  é obrigatório")
@ManyToOne
@JoinColumn(name = "codigo_conta")
private Conta conta;

@OneToMany(mappedBy = "cliente")
private List<Proposta> propostas;


@PrePersist
@PreUpdate
private void prePersistUpdate() {
    nome = nome.toUpperCase();
    sobrenome = sobrenome.toUpperCase();
    email   = email.toUpperCase();
}



public Long getCodigo() {
    return codigo;
}

public void setCodigo(Long codigo) {
    this.codigo = codigo;
}

public String getNome() {
    return nome;
}

public void setNome(String nome) {
    this.nome = nome;
}

public String getSobrenome() {
    return sobrenome;
}

public void setSobrenome(String sobrenome) {
    this.sobrenome = sobrenome;
}

public String getEmail() {
    return email;
}

public void setEmail(String email) {
    this.email = email;
}

public String getTelefone() {
    return telefone;
}

public void setTelefone(String telefone) {
    this.telefone = telefone;
}

public String getCpf() {
    return cpf;
}

public void setCpf(String cpf) {
    this.cpf = cpf;
}

public String getRg() {
    return rg;
}

public void setRg(String rg) {
    this.rg = rg;
}

public List<Equipe> getEquipes() {
    return equipes;
}

public void setEquipes(List<Equipe> equipes) {
    this.equipes = equipes;
}

public Genero getGenero() {
    return genero;
}

public void setGenero(Genero genero) {
    this.genero = genero;
}

public Conta getConta() {
    return conta;
}

public void setConta(Conta conta) {
    this.conta = conta;
}

public List<Proposta> getPropostas() {
    return propostas;
}

public void setPropostas(List<Proposta> propostas) {
    this.propostas = propostas;
}

@Override
public int hashCode() {
    final int prime = 31;
    int result = 1;
    result = prime * result + ((codigo == null) ? 0 : codigo.hashCode());
    return result;
}

@Override
public boolean equals(Object obj) {
    if (this == obj)
        return true;
    if (obj == null)
        return false;
    if (getClass() != obj.getClass())
        return false;
    Cliente other = (Cliente) obj;
    if (codigo == null) {
        if (other.codigo != null)
            return false;
    } else if (!codigo.equals(other.codigo))
        return false;
    return true;
}

public Cliente(Long codigo, String nome, String sobrenome, String email, String telefone, String cpf, String rg,
        List<Equipe> equipes, Genero genero, Conta conta, List<Proposta> propostas) {
    super();
    this.codigo = codigo;
    this.nome = nome;
    this.sobrenome = sobrenome;
    this.email = email;
    this.telefone = telefone;
    this.cpf = cpf;
    this.rg = rg;
    this.equipes = equipes;
    this.genero = genero;
    this.conta = conta;
    this.propostas = propostas;
}

public Cliente() {
    super();
}

}

I'm going to post the ProFilter code:

package com.bss.sistema.genesis.repository.filter;

import java.math.BigDecimal;   
import com.bss.sistema.genesis.model.Banco;
import com.bss.sistema.genesis.model.Cliente;
import com.bss.sistema.genesis.model.Produto;
import com.bss.sistema.genesis.model.Tabela;

public class PropostaFilter {


private String ade;
private Cliente cliente;
private Banco banco;
private Produto produto;
private Tabela tabela;
private BigDecimal valorDe;
private BigDecimal valorAte;

public String getAde() {
    return ade;
}

public void setAde(String ade) {
    this.ade = ade;
}

public Cliente getCliente() {
    return cliente;
}

public void setCliente(Cliente cliente) {
    this.cliente = cliente;
}

public Banco getBanco() {
    return banco;
}

public void setBanco(Banco banco) {
    this.banco = banco;
}

public Produto getProduto() {
    return produto;
}

public void setProduto(Produto produto) {
    this.produto = produto;
}

public Tabela getTabela() {
    return tabela;
}

public void setTabela(Tabela tabela) {
    this.tabela = tabela;
}

public BigDecimal getValorDe() {
    return valorDe;
}

public void setValorDe(BigDecimal valorDe) {
    this.valorDe = valorDe;
}

public BigDecimal getValorAte() {
    return valorAte;
}

public void setValorAte(BigDecimal valorAte) {
    this.valorAte = valorAte;
}

}

#

ProposalImpl:

package com.bss.sistema.genesis.repository.helper.proposta;

import java.util.List;

import javax.persistence.EntityManager;
import javax.persistence.PersistenceContext;

import org.hibernate.Criteria;
import org.hibernate.Session;
import org.hibernate.criterion.Restrictions;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.StringUtils;

import com.bss.sistema.genesis.model.Proposta;
import com.bss.sistema.genesis.repository.filter.PropostaFilter;

public class PropostasImpl implements PropostasQueries {


@PersistenceContext
private EntityManager manager;
// Criando a Criteria para Usuario = filtro
// Pra pegar a criteria do Hibernate precisa de uma transacao , apenas de
// leitura

@SuppressWarnings("unchecked")
@Override
@Transactional(readOnly = true)
public List<Proposta> filtrar(PropostaFilter filtro) {
    Criteria criteria = manager.unwrap(Session.class).createCriteria(Proposta.class);
    if (filtro != null) {

        if (!StringUtils.isEmpty(filtro.getAde())) {
            criteria.add(Restrictions.eq("ade", filtro.getAde()));
        }

        if (isClientePresente(filtro)) {
            criteria.add(Restrictions.eq("cliente", filtro.getCliente()));
        }
        if (isBancoPresente(filtro)) {
            criteria.add(Restrictions.eq("banco", filtro.getBanco()));
        }

        if (isProdutoPresente(filtro)) {
            criteria.add(Restrictions.eq("produto", filtro.getProduto()));
        }

        if (isTabelaPresente(filtro)) {
            criteria.add(Restrictions.eq("tabela", filtro.getTabela()));
        }

    }
    return criteria.list();
}

private boolean isProdutoPresente(PropostaFilter filtro) {
    return filtro.getProduto() != null && filtro.getProduto().getCodigo() != null;
}

private boolean isTabelaPresente(PropostaFilter filtro) {
    return filtro.getTabela() != null && filtro.getTabela().getCodigo() != null;
}

private boolean isClientePresente(PropostaFilter filtro) {
    return filtro.getCliente() != null && filtro.getCliente().getCodigo() != null;
}

private boolean isBancoPresente(PropostaFilter filtro) {
    return filtro.getBanco() != null && filtro.getBanco().getCodigo() != null;

}

}

ProposalQueries:

package com.bss.sistema.genesis.repository.helper.proposta;

import java.util.List;
import com.bss.sistema.genesis.model.Proposta;
import com.bss.sistema.genesis.repository.filter.PropostaFilter;

// O NOME DA INTERFACE SEMPRE NO PLURAL !!!  SE NAO NAO ACHA NA CONTROLLER
public interface PropostasQueries {
public List<Proposta> filtrar (PropostaFilter filtro); 

}

HTML:

<head>
    <title>Pesquisa de propostas</title>
</head>

<body>
<section layout:fragment="conteudo">
    <div class="page-header">
        <div class="container-fluid">
            <div class="row">
                <div class="col-sm-10">
                    <h1>Pesquisa de propostas</h1>
                </div>

                <div class="col-sm-2">
                    <div class="aw-page-header-controls">
                        <a class="btn  btn-default" th:href="@{/propostas/novo}">
                            <i class="glyphicon  glyphicon-plus-sign"></i> <span class="hidden-xs  hidden-sm">Nova proposta</span>
                        </a>
                    </div>
                </div>
            </div>
        </div>
    </div>

        <div class="container-fluid">
            <form  method="GET" th:object="${propostaFilter}">

                <!--  Inicio DIV ADE - CLIENTE -->
                <div class="row">

                <div class="form-group col-sm-4">
                <label class="control-label" for="ade">ADE</label>
                <input type="text" class="form-control" id="ade" autofocus="autofocus" th:field="*{ade}"/>
                </div>


                <div class="form-group col-sm-4">
                <label class="control-label" for="cpf">CPF</label>
                <input type="text" class="form-control" id="cpf" autofocus="autofocus"  th:field="*{cliente.cpf}"/>
                </div>





                </div>
                        <!--  FIM DIV ADE - CLIENTE -->


                <!--  INICIO DIV BANCO  | PRODUTO | TABELA -->
                <div class="row">
                <div class="form-group col-sm-4">
                <label class="control-label" for="banco">Banco</label>
                <select id="banco" class="form-control" th:field=*{banco}>
                <option value="">Todos os Bancos</option>
                <option th:each="banco : ${bancos}" th:value="${banco.codigo}" th:text="${banco.nome}"></option>
                </select>
                </div>


                <div class="form-group col-sm-4">
                <label class="control-label" for="produto">Produto</label>
                <select id="produto" class="form-control" th:field=*{produto}>
                <option value="">Todos os Produtos</option>
                <option th:each="produto : ${produtos}"th:value="${produto.codigo}" th:text="${produto.descricao}"></option>
                </select>
                </div>


                <div class="form-group col-sm-4">
                <label class="control-label" for="produto">Tabela</label>
                <select id="produto" class="form-control" th:field=*{tabela}>
                <option value="">Todos as Tabelas</option>
                <option th:each="tabela : ${tabelas}"th:value="${tabela.codigo}" th:text="${tabela.descricao}"></option>
                </select>
                </div>
                </div>
                <!--  END DIV | PRODUTO | TABELA -->



                <!--  Inicio DIV |PERIODO | VALOR-->
                <div class="row">

                <div class="col-sm-6  form-group">
                <label for="periodo">Período</label>
                <div class="form-inline">
                    <input type="date" class="form-control  gn-form-control-inline-sm  js-decimal" id="dataIni"/>
                    <label for="periodo" class="gn-form-label-between">até</label>
                    <input type="date" class="form-control  gn-form-control-inline-sm  js-decimal" id="dataFim"/>
                </div>
            </div>




                <div class="col-sm-6  form-group">
                <label for="valorDe">Valor Total</label>
                <div class="form-inline">
                    <input type="text" class="form-control  gn-form-control-inline-sm  js-decimal" id="valorDe" th:field=*{valorDe}>
                    <label for="precoAte" class="gn-form-label-between">até</label>
                    <input type="text" class="form-control  gn-form-control-inline-sm  js-decimal" id="valorAte" th:field=*{valorAte}>
                </div>
            </div>
        </div>
            <!--  Inicio DIV |PERIODO | VALOR-->


            <!--  FIM DIV CONTA | DATA NASC | GRUPO-->

        <div class="form-group">
        <button type="submit" class="btn  btn-primary">Pesquisar</button>
    </div>

                </form>




        <!-- INICIO DIV TABLES -->
        <div class="table-responsive gn-tabela-simples" >
        <table class="table table-hover">
            <thead>
                <tr>
                <th class="table-propostas-col-ade">ADE</th>
                    <th class="table-propostas-col-cpf">CPF</th>
                    <th class="table-propostas-col-banco">Banco</th>
                    <th class="table-propostas-col-produto">Produto</th>
                    <th class="table-propostas-col-produto">Tabela</th>
                    <th class="table-propostas-col-valorTotal">Valor</th>
                    <th class="table-propostas-col-dataProposta">Data</th>
                    <th class="table-propostas-col-acoes"></th>
                </tr>
                </thead>
                <tbody>

                <tr th:each="proposta : ${propostas}">
                    <td class="text-center" th:text="${proposta.ade}"></td>
                    <td th:text="${proposta.cliente.cpf}"></td>
                    <td th:text="${proposta.banco.nome}"></td>
                    <td th:text="${proposta.produto.descricao}"></td>
                    <td th:text="${proposta.tabela.descricao}"></td>
                    <td th:text="|R$ ${proposta.valorTotal}|"></td>
                    <td th:text="${proposta.dataProposta}">10/05/2018</td>
                    <td class="text-center">
                        <a class="btn  btn-link  btn-xs" title="Editar"> 
                            <i class="glyphicon glyphicon-pencil"></i>
                        </a>
                        <a class="btn  btn-link  btn-xs" title="Excluir">
                            <i class="glyphicon glyphicon-remove"></i>
                        </a>
                    </td>
                </tr>
            </tbody>    
        </table>
        </div>
            <!-- FIM  DIV TABLES -->
    </div>

Who can help, thank you.

    
asked by anonymous 11.05.2018 / 04:18

2 answers

2

You need to add JOIN between Proposal and Client, like this:

// veja que adicionei um alias chamado "proposta"
Criteria criteria = manager.unwrap(Session.class).createCriteria(Proposta.class, "proposta");
// JOIN entre proposta e cliente, imaginando que na entidade proposta o campo que armazena a entidade cliente chame-se "cliente" mesmo
criteria.createAlias("proposta.cliente", "cliente");
// adiciona a restrição
criteria.add(Restrictions.eq("cliente.cpf", "123.123.123-12"));

In your current code, there are several ways to embed this code. If you are in doubt about this organization, I suggest opening a new question. Here is an example that, although it does not make much sense in practice (if you fetch the client by ID, it does not make sense to fetch it by CPF), but it gives you an idea of how you can compose:

Criteria criteria = manager.unwrap(Session.class).createCriteria(Proposta.class, "proposta");
if (filtro != null) {

    if (isClientePresente(filtro)) {

        criteria.createAlias("proposta.cliente", "cliente");
        criteria.add(Restrictions.eq("cliente", filtro.getCliente)); // na prática, é uma busca por id de cliente

        if (isCpfClientePresente(filtro)) {
            criteria.add(Restrictions.eq("cliente.cpf", "123.123.123-12"));
        }
    }

    // outros filtros
}
    
11.05.2018 / 13:50
0
@Transactional(readOnly = true)
public List<Proposta> filtrar(String CPF) {
    CriteriaBuilder builder = manager.getCriteriaBuilder();
    CriteriaQuery<Proposta> query = builder.createQuery(Proposta.class);

    Root<Proposta> root = query.from(Proposta.class);

    query.select(root);
    Join<Object, Object> joinCliente = root.join("cliente");//faz o inner join com o cliente e cria um ojeto cliente na query       

    /*
     * adiciona pesquisa da proposta pelo cpf do cliente
     * O where aceita um array de Predicate caso use mais de uma clausula
     */
    query.where(builder.equal(joinCliente.get("cpf"), CPF));


    TypedQuery<Proposta> typedQuery = manager.createQuery(query.distinct(true));


    return typedQuery.getResultList();
}
    
11.05.2018 / 14:43