Problema ao inserir dados usando Hibernate e JSF

2 respostas
S

Boa tarde galera.

Estou aqui por que estou com um problema ao inserir dados no mysql utilizando o hibernate.

Eu tenho 3 classes com as anotações do hibernate: NotaFiscal, Item e Produto.

Na NotaFiscal eu tenho um List
E no Item eu tenho um objeto Produto

Se eu clicar em gravar a nota fiscal sem ter adicionado nenhum intem ele grava no banco normal.
Mas se eu adicionar itens na Nota e depois for gravar-la, gera um erro .
Ja pesquiseii muittoo na net e ainda não consegui sair do lugar =/

Alguem pode me ajudar.?

[color=red]notafiscal.xhtml[/color]

<html xmlns="http://www.w3.org/1999/xhtml"
      xmlns:ui="http://java.sun.com/jsf/facelets"
      xmlns:f="http://java.sun.com/jsf/core"
      xmlns:h="http://java.sun.com/jsf/html"
      xmlns:p="http://primefaces.prime.com.tr/ui">
  
  <h:body>
    
    <div id="blocoConteudo">
      <div class="container">
      
      <h:messages />
      
	    <h2>Cadastro de nots fiscais</h2>
	    
	    <h:form>
	      <fieldset>
	        
	        <legend>Dados do produto</legend>
		    <h:outputLabel value="Produto:"/>
		    <h:selectOneMenu value="#{notaFiscalBean.idProduto}">
	          <f:selectItems value="#{produtoBean.produtos}" var="p" itemValue="#{p.id}" itemLabel="#{p.nome}" />
	        </h:selectOneMenu>
	        <br />
	        <h:outputLabel value="Quantidade:"/>
	        <h:inputText value="#{notaFiscalBean.item.quantidade}"/>
	        <br />
	        <h:commandButton action="#{notaFiscalBean.adicionaItem}" value="Adicionar Item"/>
	      
	      </fieldset>
	    </h:form>
	    
	    <h:form>
	    
	    <fieldset>
	      
	        <legend>Dados da nota</legend>
	        <h:outputLabel value="CNPJ Cliente:"/>
	        <h:inputText value="#{notaFiscalBean.notaFiscal.cnpj}"/>
	        <br />
	        <h:outputLabel value="Data:"/>
	        <p:calendar patterm="dd/MM/yyyy" value="#{notaFiscalBean.notaFiscal.data}"/>
	        
	      </fieldset>
	      
	      <h2>Itens da nota fiscal</h2>
	      <h:dataTable value="#{notaFiscalBean.notaFiscal.itens}" var="item" styleClass="dados" rowClasses="impar,par" >
	        <h:column>
	          <f:facet name="header">
	            <h:outputText value="Produto"/>
	          </f:facet>
	          <h:outputText value="#{item.produto.nome}"/>
	        </h:column>
	        <h:column>
	          <f:facet name="header">
	            <h:outputText value="Preco"/>
	          </f:facet>
	          <h:outputText value="#{item.valorUnitario}">
	            <f:convertNumber pattern="R$ #0.00"/>
	          </h:outputText>
	        </h:column>
	        <h:column>
	          <f:facet name="header">
	            <h:outputText value="Quantidade"/>
	          </f:facet>
	          <h:outputText value="#{item.quantidade}"/>
	        </h:column>
	        <h:column>
	          <f:facet name="header">
	            <h:outputText value="Valor"/>
	          </f:facet>
	          <h:outputText value="#{item.total}">
	            <f:convertNumber pattern="R$ #0.00"/>
	          </h:outputText>
	        </h:column>
	      </h:dataTable>
	      
	      <h:commandButton value="Gravar" action="#{notaFiscalBean.adiciona}"/>
	      
	    </h:form>
      
      </div>
    </div>
  
  </h:body>

</html>

[color=red]NotaFiscalBean.java[/color]

package br.com.nf.mb;

import javax.faces.bean.ManagedBean;
import javax.faces.bean.ViewScoped;

import br.com.nf.dao.DAO;
import br.com.nf.modelo.Item;
import br.com.nf.modelo.NotaFiscal;
import br.com.nf.modelo.Produto;

@ViewScoped
@ManagedBean
public class NotaFiscalBean {

	private Item item = new Item();
	private NotaFiscal notaFiscal = new NotaFiscal();
	private Long idProduto;
	
	public void setIdProduto(Long idProduto) {
		this.idProduto = idProduto;
	}
	
	public Long getIdProduto() {
		return this.idProduto;
	}

	public Item getItem() {
		return this.item;
	}
	
	public NotaFiscal getNotaFiscal() {
		return this.notaFiscal;
	}
	
	public void adicionaItem() {
		DAO<Produto> dao = new DAO<Produto>(Produto.class);
		Produto produto = dao.buscaPorId(idProduto);
		item.setProduto(produto);
		item.setValorUnitario(produto.getPreco());
		
		notaFiscal.adicionaItem(item);
		item = new Item();
	}
	
	public void adiciona() {
		DAO<NotaFiscal> dao = new DAO<NotaFiscal>(NotaFiscal.class);
		dao.adiciona(notaFiscal);
		notaFiscal = new NotaFiscal();
	}
	
}

[color=red]DAO.java[/color]

package br.com.nf.dao;

import java.util.List;

import javax.persistence.EntityManager;
import javax.persistence.criteria.CriteriaQuery;

public class DAO<T> {
	private final Class<T> classe;

	public DAO(Class<T> classe) {
		this.classe = classe;
	}

	public void adiciona(T t) {
		// consegue a entity manager
		EntityManager em = new JPAUtil().getEntityManager();
		// abre transacao
		em.getTransaction().begin();

		// persiste o objeto
		em.persist(t);

		// commita a transacao
		em.getTransaction().commit();

		// fecha a entity manager
		em.close();
	}

	public void remove(T t) {
		EntityManager em = new JPAUtil().getEntityManager();
		em.getTransaction().begin();

		em.remove(em.merge(t));

		em.getTransaction().commit();
		em.close();
	}

	public void atualiza(T t) {
		EntityManager em = new JPAUtil().getEntityManager();
		em.getTransaction().begin();

		em.merge(t);

		em.getTransaction().commit();
		em.close();
	}

	public List<T> listaTodos() {
		EntityManager em = new JPAUtil().getEntityManager();
		CriteriaQuery<T> query = em.getCriteriaBuilder().createQuery(classe);
		query.select(query.from(classe));

		List<T> lista = em.createQuery(query).getResultList();

		em.close();
		return lista;
	}

	public T buscaPorId(long id) {
		EntityManager em = new JPAUtil().getEntityManager();
		return em.find(classe, id);

	}

}

[color=red]NotaFiscal.java[/color]

package br.com.nf.modelo;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;

import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.OneToMany;
import javax.persistence.Temporal;
import javax.persistence.TemporalType;
import javax.validation.constraints.Pattern;

import br.com.nf.modelo.Item;

@Entity
public class NotaFiscal {

	@Id
	@GeneratedValue
	private Long id;
	@Pattern(regexp="(\\d{2})[.](\\d{3})[.](\\d{3})/(\\d{4})-(\\d{2})", message="CNPJ Inválido.!")
	private String cnpj;
	@Temporal(TemporalType.DATE)
	private Date data;
	@OneToMany
	private List<Item> itens;
	
	public Long getId() {
		return id;
	}
	public void setId(Long id) {
		this.id = id;
	}
	public String getCnpj() {
		return cnpj;
	}
	public void setCnpj(String cnpj) {
		this.cnpj = cnpj;
	}
	public Date getData() {
		return data;
	}
	public void setData(Date data) {
		this.data = data;
	}
	public List<Item> getItens() {
		return itens;
	}
	public void setItens(List<Item> itens) {
		this.itens = itens;
	}
	public void adicionaItem(Item item) {
		if (this.itens == null) {
			this.itens = new ArrayList<Item>();
		}
		this.itens.add(item);
	}
}

[color=red]Item.java[/color]

package br.com.nf.modelo;

import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.ManyToOne;

@Entity
public class Item {

	@Id
	@GeneratedValue
	private Long id;
	@ManyToOne
	private Produto produto;
	private Integer quantidade;
	private Double valorUnitario;
	private Double total;
	
	public Double getTotal() {
		return total;
	}
	public void setTotal(Double total) {
		this.total = total;
	}
	public Long getId() {
		return id;
	}
	public void setId(Long id) {
		this.id = id;
	}
	public Produto getProduto() {
		return produto;
	}
	public void setProduto(Produto produto) {
		this.produto = produto;
	}
	public Integer getQuantidade() {
		return quantidade;
	}
	public void setQuantidade(Integer quantidade) {
		this.quantidade = quantidade;
	}
	public Double getValorUnitario() {
		return valorUnitario;
	}
	public void setValorUnitario(Double valorUnitario) {
		this.valorUnitario = valorUnitario;
	}
	
}

[color=red]Produto.java[/color]

package br.com.nf.modelo;

import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;

import org.hibernate.validator.constraints.NotEmpty;


@Entity
public class Produto {
	
	@Id
	@GeneratedValue
	private Long id;
	@NotEmpty(message="Nome inválido.!")
	private String nome;
	private String descricao;
	private Double preco;
	
	public Long getId() {
		return id;
	}
	public void setId(Long id) {
		this.id = id;
	}
	public String getNome() {
		return nome;
	}
	public void setNome(String nome) {
		this.nome = nome;
	}
	public String getDescricao() {
		return descricao;
	}
	public void setDescricao(String descricao) {
		this.descricao = descricao;
	}
	public Double getPreco() {
		return preco;
	}
	public void setPreco(Double preco) {
		this.preco = preco;
	}
	
}

[color=red]O erro gerado é esse :[/color]

description The server encountered an internal error () that prevented it from fulfilling this request.

exception 

javax.servlet.ServletException: javax.persistence.RollbackException: Error while committing the transaction
	javax.faces.webapp.FacesServlet.service(FacesServlet.java:321)


root cause 

javax.faces.el.EvaluationException: javax.persistence.RollbackException: Error while committing the transaction
	javax.faces.component.MethodBindingMethodExpressionAdapter.invoke(MethodBindingMethodExpressionAdapter.java:98)
	com.sun.faces.application.ActionListenerImpl.processAction(ActionListenerImpl.java:98)
	javax.faces.component.UICommand.broadcast(UICommand.java:311)
	javax.faces.component.UIViewRoot.broadcastEvents(UIViewRoot.java:781)
	javax.faces.component.UIViewRoot.processApplication(UIViewRoot.java:1246)
	com.sun.faces.lifecycle.InvokeApplicationPhase.execute(InvokeApplicationPhase.java:77)
	com.sun.faces.lifecycle.Phase.doPhase(Phase.java:97)
	com.sun.faces.lifecycle.LifecycleImpl.execute(LifecycleImpl.java:114)
	javax.faces.webapp.FacesServlet.service(FacesServlet.java:308)


root cause 

javax.persistence.RollbackException: Error while committing the transaction
	org.hibernate.ejb.TransactionImpl.commit(TransactionImpl.java:93)
	br.com.nf.dao.DAO.adiciona(DAO.java:25)
	br.com.nf.mb.NotaFiscalBean.adiciona(NotaFiscalBean.java:47)
	sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
	sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
	java.lang.reflect.Method.invoke(Method.java:597)
	org.apache.el.parser.AstValue.invoke(AstValue.java:191)
	org.apache.el.MethodExpressionImpl.invoke(MethodExpressionImpl.java:276)
	com.sun.faces.facelets.el.TagMethodExpression.invoke(TagMethodExpression.java:102)
	javax.faces.component.MethodBindingMethodExpressionAdapter.invoke(MethodBindingMethodExpressionAdapter.java:84)
	com.sun.faces.application.ActionListenerImpl.processAction(ActionListenerImpl.java:98)
	javax.faces.component.UICommand.broadcast(UICommand.java:311)
	javax.faces.component.UIViewRoot.broadcastEvents(UIViewRoot.java:781)
	javax.faces.component.UIViewRoot.processApplication(UIViewRoot.java:1246)
	com.sun.faces.lifecycle.InvokeApplicationPhase.execute(InvokeApplicationPhase.java:77)
	com.sun.faces.lifecycle.Phase.doPhase(Phase.java:97)
	com.sun.faces.lifecycle.LifecycleImpl.execute(LifecycleImpl.java:114)
	javax.faces.webapp.FacesServlet.service(FacesServlet.java:308)


root cause 

java.lang.IllegalStateException: org.hibernate.TransientObjectException: object references an unsaved transient instance - save the transient instance before flushing: br.com.nf.modelo.Item
	org.hibernate.ejb.AbstractEntityManagerImpl.convert(AbstractEntityManagerImpl.java:1176)
	org.hibernate.ejb.AbstractEntityManagerImpl.convert(AbstractEntityManagerImpl.java:1112)
	org.hibernate.ejb.TransactionImpl.commit(TransactionImpl.java:81)
	br.com.nf.dao.DAO.adiciona(DAO.java:25)
	br.com.nf.mb.NotaFiscalBean.adiciona(NotaFiscalBean.java:47)
	sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
	sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
	java.lang.reflect.Method.invoke(Method.java:597)
	org.apache.el.parser.AstValue.invoke(AstValue.java:191)
	org.apache.el.MethodExpressionImpl.invoke(MethodExpressionImpl.java:276)
	com.sun.faces.facelets.el.TagMethodExpression.invoke(TagMethodExpression.java:102)
	javax.faces.component.MethodBindingMethodExpressionAdapter.invoke(MethodBindingMethodExpressionAdapter.java:84)
	com.sun.faces.application.ActionListenerImpl.processAction(ActionListenerImpl.java:98)
	javax.faces.component.UICommand.broadcast(UICommand.java:311)
	javax.faces.component.UIViewRoot.broadcastEvents(UIViewRoot.java:781)
	javax.faces.component.UIViewRoot.processApplication(UIViewRoot.java:1246)
	com.sun.faces.lifecycle.InvokeApplicationPhase.execute(InvokeApplicationPhase.java:77)
	com.sun.faces.lifecycle.Phase.doPhase(Phase.java:97)
	com.sun.faces.lifecycle.LifecycleImpl.execute(LifecycleImpl.java:114)
	javax.faces.webapp.FacesServlet.service(FacesServlet.java:308)


root cause 

org.hibernate.TransientObjectException: object references an unsaved transient instance - save the transient instance before flushing: br.com.nf.modelo.Item
	org.hibernate.engine.ForeignKeys.getEntityIdentifierIfNotUnsaved(ForeignKeys.java:244)
	org.hibernate.type.EntityType.getIdentifier(EntityType.java:449)
	org.hibernate.type.ManyToOneType.nullSafeSet(ManyToOneType.java:132)
	org.hibernate.persister.collection.AbstractCollectionPersister.writeElement(AbstractCollectionPersister.java:816)
	org.hibernate.persister.collection.AbstractCollectionPersister.recreate(AbstractCollectionPersister.java:1204)
	org.hibernate.action.CollectionRecreateAction.execute(CollectionRecreateAction.java:58)
	org.hibernate.engine.ActionQueue.execute(ActionQueue.java:268)
	org.hibernate.engine.ActionQueue.executeActions(ActionQueue.java:260)
	org.hibernate.engine.ActionQueue.executeActions(ActionQueue.java:183)
	org.hibernate.event.def.AbstractFlushingEventListener.performExecutions(AbstractFlushingEventListener.java:321)
	org.hibernate.event.def.DefaultFlushEventListener.onFlush(DefaultFlushEventListener.java:51)
	org.hibernate.impl.SessionImpl.flush(SessionImpl.java:1206)
	org.hibernate.impl.SessionImpl.managedFlush(SessionImpl.java:375)
	org.hibernate.transaction.JDBCTransaction.commit(JDBCTransaction.java:137)
	org.hibernate.ejb.TransactionImpl.commit(TransactionImpl.java:76)
	br.com.nf.dao.DAO.adiciona(DAO.java:25)
	br.com.nf.mb.NotaFiscalBean.adiciona(NotaFiscalBean.java:47)
	sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
	sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
	java.lang.reflect.Method.invoke(Method.java:597)
	org.apache.el.parser.AstValue.invoke(AstValue.java:191)
	org.apache.el.MethodExpressionImpl.invoke(MethodExpressionImpl.java:276)
	com.sun.faces.facelets.el.TagMethodExpression.invoke(TagMethodExpression.java:102)
	javax.faces.component.MethodBindingMethodExpressionAdapter.invoke(MethodBindingMethodExpressionAdapter.java:84)
	com.sun.faces.application.ActionListenerImpl.processAction(ActionListenerImpl.java:98)
	javax.faces.component.UICommand.broadcast(UICommand.java:311)
	javax.faces.component.UIViewRoot.broadcastEvents(UIViewRoot.java:781)
	javax.faces.component.UIViewRoot.processApplication(UIViewRoot.java:1246)
	com.sun.faces.lifecycle.InvokeApplicationPhase.execute(InvokeApplicationPhase.java:77)
	com.sun.faces.lifecycle.Phase.doPhase(Phase.java:97)
	com.sun.faces.lifecycle.LifecycleImpl.execute(LifecycleImpl.java:114)
	javax.faces.webapp.FacesServlet.service(FacesServlet.java:308)

2 Respostas

R

olhando o mapeamento estou vendo que ta faltando mapear os relacionamentos de forma bidirecional, ou seja vc precisa definir o relacionamento duas vezes, pois o Hibernate precisa saber que o lado @ManyToOne qto o @OneToMany pertencem ao mesmo relacionamento.

S

Rodrigo.
Valeu.

Fiz do jeito que você mostrou e funcionou.

Obrigado mesmo em.

Pensei que como outros foruns, não iam responder meu post, mas vi que aqui o pessoa gosta de ajudar. :smiley:

Obrigado,
Abraços.!

Criado 7 de agosto de 2010
Ultima resposta 7 de ago. de 2010
Respostas 2
Participantes 2