Solucionado (ver solução)
Solucionado
(ver solução)
5
respostas

Erro ao salvar dados do libro (18 Inserindo os Dados no Banco de Dados)

Prezados ao tentar salvar o livro, esta laçando o seguinte erro:

HTTP Status 500 - java.lang.NullPointerException

type Exception report

message java.lang.NullPointerException

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

exception

javax.servlet.ServletException: java.lang.NullPointerException
    javax.faces.webapp.FacesServlet.service(FacesServlet.java:671)
    org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:52)

root cause

javax.faces.el.EvaluationException: java.lang.NullPointerException
    javax.faces.component.MethodBindingMethodExpressionAdapter.invoke(MethodBindingMethodExpressionAdapter.java:101)
    com.sun.faces.application.ActionListenerImpl.processAction(ActionListenerImpl.java:102)
    javax.faces.component.UICommand.broadcast(UICommand.java:315)
    javax.faces.component.UIViewRoot.broadcastEvents(UIViewRoot.java:790)
    javax.faces.component.UIViewRoot.processApplication(UIViewRoot.java:1282)
    com.sun.faces.lifecycle.InvokeApplicationPhase.execute(InvokeApplicationPhase.java:81)
    com.sun.faces.lifecycle.Phase.doPhase(Phase.java:101)
    com.sun.faces.lifecycle.LifecycleImpl.execute(LifecycleImpl.java:198)
    javax.faces.webapp.FacesServlet.service(FacesServlet.java:658)
    org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:52)

root cause

java.lang.NullPointerException
    br.com.lacc.livraria.daos.LivroDao.salvar(LivroDao.java:19)
    br.com.lacc.livraria.beans.AdminLivrosBean.salvar(AdminLivrosBean.java:23)
    sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    java.lang.reflect.Method.invoke(Method.java:498)
    org.apache.el.parser.AstValue.invoke(AstValue.java:279)
    org.apache.el.MethodExpressionImpl.invoke(MethodExpressionImpl.java:273)
    org.jboss.weld.util.el.ForwardingMethodExpression.invoke(ForwardingMethodExpression.java:40)
    org.jboss.weld.el.WeldMethodExpression.invoke(WeldMethodExpression.java:50)
    com.sun.faces.facelets.el.TagMethodExpression.invoke(TagMethodExpression.java:105)
    javax.faces.component.MethodBindingMethodExpressionAdapter.invoke(MethodBindingMethodExpressionAdapter.java:87)
    com.sun.faces.application.ActionListenerImpl.processAction(ActionListenerImpl.java:102)
    javax.faces.component.UICommand.broadcast(UICommand.java:315)
    javax.faces.component.UIViewRoot.broadcastEvents(UIViewRoot.java:790)
    javax.faces.component.UIViewRoot.processApplication(UIViewRoot.java:1282)
    com.sun.faces.lifecycle.InvokeApplicationPhase.execute(InvokeApplicationPhase.java:81)
    com.sun.faces.lifecycle.Phase.doPhase(Phase.java:101)
    com.sun.faces.lifecycle.LifecycleImpl.execute(LifecycleImpl.java:198)
    javax.faces.webapp.FacesServlet.service(FacesServlet.java:658)

Como se o objeto Livro não estivesse instanciado, mais ele esta sendo inicializado na classe AdminLivrosBean, como pode ser visto:

import javax.enterprise.context.RequestScoped;
import javax.inject.Inject;
import javax.inject.Named;
import javax.transaction.Transactional;

@Named
@RequestScoped
public class AdminLivrosBean {

    private Livro livro = new Livro();

    @Inject
    private LivroDao dao;

    @Transactional
    public void salvar() {
        dao.salvar(livro);
    }
    public Livro getLivro() {  return livro; }

    public void setLivro(Livro livro) {  this.livro = livro; }
}

A clase LivroDao esta assim:

package br.com.lacc.livraria.daos;
import br.com.lacc.livraria.models.Livro;

import javax.persistence.EntityManager;
import javax.persistence.PersistenceContext;
import java.io.Serializable;

public class LivroDao implements Serializable {

    private static final long serialVersionUID = 1L;

    @PersistenceContext
    private EntityManager manager;


    public void salvar(Livro livro) {
        System.out.println("Livro|| " + livro);  //OS DADOS PASSADOS PELO FORMULÁRIO CHEGAM ATÉ AQUI
        manager.persist(livro);
    }
}

No método salvar, os dados do objeto livro vindo do formulário chegam sem problemas antes de fazer o manager.persist:

Livro|| Livro{titulo='Dia D', descricao='segunda guerra mundial', preco=30.0, numeroDePaginas=120}

Que pode estar acontecendo?

Obrigado pela atenção.

5 respostas

Boa noite, Luis! Como vai?

A stacktrace está acusando um NullPointerException na linha 19 do arquivo LivroDao.

java.lang.NullPointerException
    br.com.lacc.livraria.daos.LivroDao.salvar(LivroDao.java:19)

A linha 19 desse arquivo é essa aqui, correto?

manager.persist(livro);

Se eu estiver correto, a sua instância de EntityManager está nula, por isso vc está obtendo esse erro!

Agora falta descobrir pq a instância está vindo nula! Pode ser alguma configuração incorreta que vc tenha feito no seu projeto.

Verifique aí as configurações que vc fez e qualquer coisa é só voltar a comentar aqui!

Grande abraço!

Olá Gabriel, A instancia do EntityManager esta nulla, não sei o por que o @PersistenceContext não consegue fazer a injeção. Para solucionar esse problema tive que criar um objeto factory para retornar essa EM:

public class JPAUtil {

    private static EntityManagerFactory emf = Persistence.createEntityManagerFactory("projeto_livraria");

    public EntityManager getEntityManager() {
        return emf.createEntityManager();
    }
}

E chamo ela no livroDao:

@PersistenceContext
    private EntityManager manager = new JPAUtil().getEntityManager();

    public void salvar(Livro livro) {
        manager.getTransaction().begin();
        manager.persist(livro);
        manager.getTransaction().commit();
        manager.close();
    }

Dessa forma consigo inserir no BD, mais sempre terei que criar uma transação, comitar e fechar para poder fazer isso, (poderia criar uma classe Dao para abstrair tudo isso) , porem, no curso o @PersistenceContext faria o trabalho sujo, sinceramente não sei o que poderia estar errado, fiquei horas tentando sem sucesso :(

Como poderia contornar isso? Se não for muito pedir, poderia dar uma olhada no meu projeto? Obrigado.

Boa tarde, Luis! Provavelmente, como eu falei antes, deve ter algum problema na configuração do seu projeto. Pode ser que vc tenha esquecido de fazer algum passo visto em aula.

Para que eu possa tentar te ajudar, poste aqui o conteúdo dos arquivos pom.xml, persistence.xml e standalone-full.xml.

solução!

Olá Gabriel, não consegui identificar o problema, assim que tive que fazer um pouco diferente para persistir os dados, criei uma anotação e um gerenciador de transação, agora sim consigo fazer a persistência dos dados.

Obrigado pela atenção Gabriel. Abs.

Que bom que vc resolveu, Luis! Mas, como eu disse, provavelmente o problema deveria ser alguma configuração que deveria estar faltando ou feita de maneira errada o que forçou vc a dar essa volta um pouco maior. Mas beleza...

Grande abraço e bons estudos!