NullPointerException 使用 Spring 使 Generic Dao 休眠

Posted

技术标签:

【中文标题】NullPointerException 使用 Spring 使 Generic Dao 休眠【英文标题】:NullPointerException hibernate Generic Dao with Spring 【发布时间】:2018-01-14 06:14:27 【问题描述】:

我有一个业务逻辑类,它尝试使用从通用 Dao 保存的 dao 方法,这是来自 bl 的代码。

public void setUsuario(Usuario usuario) 
    this.usuario = usuario;
    usuarioDao.save(usuario);

调试我发现用户对象正确填充了数据,而DaoImpl就是这个

@Component
public class UsuarioDaoImpl extends GenericDaoImpl<Usuario> implements UsuarioDao 

@Override
public Usuario get(String id) throws DataAccessException 
    // TODO Auto-generated method stub
    return null;


@Override
public boolean saveBatchFull(Collection<Usuario> entity, boolean update) throws DataAccessException 
    // TODO Auto-generated method stub
    return false;


@Override
public Usuario get(Long id) throws DataAccessException 
    // TODO Auto-generated method stub
    return null;


@Override
public boolean save(Usuario usuario) throws DataAccessException 
    super.save(usuario);
    return false;

这是我使用的通用类。

import java.lang.reflect.ParameterizedType;
import java.util.Collection;
import java.util.Iterator;
import org.slf4j.LoggerFactory;
import org.apache.log4j.LogManager;
import org.apache.logging.log4j.*;
import org.apache.log4j.LogManager;
import org.apache.log4j.Logger;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.dao.DataAccessException;
import org.springframework.transaction.annotation.Transactional;


public class GenericDaoImpl<T> implements GenericDao<T> 



       private static final Logger logger = LogManager.getLogger("GenericDaoImpl");



       protected Class<T> domainClass;



//         @Autowired(required = true)
           protected SessionFactory sessionFactory;



       // Para conexion sin Injection Dependency

       private Transaction transactionNoID;



       public GenericDaoImpl() 

             // Constructor default

       



       // Obtener el objeto

       @SuppressWarnings( "unchecked", "rawtypes" )

       protected Class<T> getDomainClass() 

             if ( domainClass == null ) 

                    ParameterizedType thisType = (ParameterizedType) getClass().getGenericSuperclass();

                    domainClass = (Class) thisType.getActualTypeArguments()[0];

             

             return domainClass;

       



       @SuppressWarnings("unchecked")

       @Transactional(readOnly = true)

       public T get(Long id) throws DataAccessException 

             Session session = null;

             if ( sessionFactory != null ) 

                    session = this.sessionFactory.getCurrentSession();

             



             String listQuery;

             StringBuilder sb = new StringBuilder(" from ");

                    sb.append(this.getDomainClass().getName());

                    sb.append(" entity ");

                    sb.append(" where id = :id ");

             listQuery = sb.toString();



             T result = null;



             if ( session == null ) 

                    session = SessionFactoryUtil.getSessionFactory().openSession();

                    try 

                           result = (T) session.createQuery(listQuery).setLong("id", id).uniqueResult();

                     catch (Exception e) 

                           e.printStackTrace();

                           logger.info("Error en la clase: " + this.getClass().getName() + " - " + e.getMessage());

                     finally 

                           session.close();

                    

              else 

                    try                      

                           result = (T) session.createQuery(listQuery).setLong("id", id).uniqueResult();

                     catch (Exception e) 

                           e.printStackTrace();

                           logger.info("Error en la clase: " + this.getClass().getName() + " - " + e.getMessage());

                    

             


             return result;

       



       @SuppressWarnings("unchecked")

       @Transactional(readOnly = true)

       public T get(String id) throws DataAccessException 

             Session session = null;

             if ( sessionFactory != null ) 

                    session = this.sessionFactory.getCurrentSession();

             



             String listQuery;

             StringBuilder sb = new StringBuilder(" from ");

                    sb.append(this.getDomainClass().getName());

                    sb.append(" entity ");

                    sb.append(" where id = :id ");

             listQuery = sb.toString();



             T result = null;



             if ( session == null ) 

                    session = SessionFactoryUtil.getSessionFactory().openSession();

                    try 

                           result = (T) session.createQuery(listQuery).setString("id", id).uniqueResult();

                     catch (Exception e) 

                           e.printStackTrace();

                           logger.info("Error en la clase: " + this.getClass().getName() + " - " + e.getMessage());

                     finally 

                           session.close();

                    

              else 

                    try                      

                           result = (T) session.createQuery(listQuery).setString("id", id).uniqueResult();

                     catch (Exception e) 

                           e.printStackTrace();

                           logger.info("Error en la clase: " + this.getClass().getName() + " - " + e.getMessage());

                    

             



             return result;

       



       @SuppressWarnings("unchecked")

       @Transactional(readOnly = true)

       public Collection<T> list() throws DataAccessException 

             Session session = null;

             if ( sessionFactory != null ) 

                    session = this.sessionFactory.getCurrentSession();

             



             String listQuery;

             StringBuilder sb = new StringBuilder(" from ");

                    sb.append(this.getDomainClass().getName());

                    sb.append(" entity ");

             listQuery = sb.toString();



             Collection<T> result = null;



             if ( session == null ) 

                    session = SessionFactoryUtil.getSessionFactory().openSession();

                    try 

                           result = session.createQuery(listQuery).list();

                     catch (Exception e) 

                           e.printStackTrace();

                           logger.info("Error en la clase: " + this.getClass().getName() + " - " + e.getMessage());

                     finally 

                           session.close();

                    

              else 

                    try                      

                           result = session.createQuery(listQuery).list();

                     catch (Exception e) 

                           e.printStackTrace();

                           logger.info("Error en la clase: " + this.getClass().getName() + " - " + e.getMessage());

                    

             



             return result;

       



       @SuppressWarnings("unchecked")

       @Transactional(readOnly = true)

       public Collection<T> listById(Long id) throws DataAccessException 

             Session session = null;

             if ( sessionFactory != null ) 

                    session = this.sessionFactory.getCurrentSession();

             



             String listQuery;

             StringBuilder sb = new StringBuilder(" from ");

                    sb.append(this.getDomainClass().getName());

                    sb.append(" entity ");

                    sb.append(" where id = :id ");

             listQuery = sb.toString();



             Collection<T> result = null;



             if ( session == null ) 

                    session = SessionFactoryUtil.getSessionFactory().openSession();

                    try 

                           result = session.createQuery(listQuery).setLong("id", id).list();

                     catch (Exception e) 

                           e.printStackTrace();

                           logger.info("Error en la clase: " + this.getClass().getName() + " - " + e.getMessage());

                     finally 

                           session.close();

                    

              else 

                    try                      

                           result = session.createQuery(listQuery).setLong("id", id).list();

                     catch (Exception e) 

                           e.printStackTrace();

                           logger.info("Error en la clase: " + this.getClass().getName() + " - " + e.getMessage());

                    

             



             return result;

       



       @SuppressWarnings("unchecked")

       @Transactional(readOnly = true)

       public Collection<T> listById(String id) throws DataAccessException 

             Session session = null;

             if ( sessionFactory != null ) 

                    session = this.sessionFactory.getCurrentSession();

             



             String listQuery;

             StringBuilder sb = new StringBuilder(" from ");

                    sb.append(this.getDomainClass().getName());

                    sb.append(" entity ");

                    sb.append(" where id = :id ");

             listQuery = sb.toString();



             Collection<T> result = null;



             if ( session == null ) 

                    session = SessionFactoryUtil.getSessionFactory().openSession();

                    try 

                           result = session.createQuery(listQuery).setString("id", id).list();

                     catch (Exception e) 

                           e.printStackTrace();

                           logger.info("Error en la clase: " + this.getClass().getName() + " - " + e.getMessage());

                     finally 

                           session.close();

                    

              else 

                    try                      

                           result = session.createQuery(listQuery).setString("id", id).list();

                     catch (Exception e) 

                           e.printStackTrace();

                           logger.info("Error en la clase: " + this.getClass().getName() + " - " + e.getMessage());

                    

             



             return result;

       



       @Transactional

       public boolean save(Object entity) throws DataAccessException 

             Session session = null;

             if ( sessionFactory != null ) 

                    session = this.sessionFactory.getCurrentSession();

             



             if ( session == null ) 

                    session = SessionFactoryUtil.getSessionFactory().openSession();

                    try 

                           transactionNoID = session.beginTransaction();

                           session.saveOrUpdate(entity);

                           transactionNoID.commit();

                           return true;

                     catch (Exception e) 

                           transactionNoID.rollback();

                           e.printStackTrace();

                           logger.info("Error en la clase: " + this.getClass().getName() + " - " + e.getMessage());

                     finally 

                           session.close();

                    

              else 

                    try                      

                           session.saveOrUpdate(entity);

                     catch (Exception e) 

                           e.printStackTrace();

                           logger.info("Error en la clase: " + this.getClass().getName() + " - " + e.getMessage());

                    

             



             return false;

       



       @Transactional

       public boolean saveNoUpdate(Object entity) throws DataAccessException 

             Session session = null;

             if ( sessionFactory != null ) 

                    session = this.sessionFactory.getCurrentSession();

             



             if ( session == null ) 

                    session = SessionFactoryUtil.getSessionFactory().openSession();

                    try 

                           transactionNoID = session.beginTransaction();

                           session.save(entity);

                           transactionNoID.commit();

                           return true;

                     catch (Exception e) 

                           transactionNoID.rollback();

                           e.printStackTrace();

                           logger.info("Error en la clase: " + this.getClass().getName() + " - " + e.getMessage());

                     finally 

                           session.close();

                    

              else 

                    try                      

                           session.save(entity);

                     catch (Exception e) 

                           e.printStackTrace();

                           logger.info("Error en la clase: " + this.getClass().getName() + " - " + e.getMessage());

                    

             



             return false;

       





       @SuppressWarnings( "unchecked", "rawtypes" )

       @Transactional

       @Override

       public boolean saveBatchFull(Collection<T> entity, boolean update) throws DataAccessException 

             Session session = null;

             if ( sessionFactory != null ) 

                    session = this.sessionFactory.getCurrentSession();

             



             if ( session == null ) 

                    session = SessionFactoryUtil.getSessionFactory().openSession();

                    try 

                           transactionNoID = session.beginTransaction();

                           for (Iterator iterator = entity.iterator(); iterator.hasNext();) 

                                  T t = (T) iterator.next();

                                  if ( update ) 

                                        session.saveOrUpdate(t);

                                   else 

                                        session.save(t);

                                  

                           

                           transactionNoID.commit();

                           return true;

                     catch (Exception e) 

                           transactionNoID.rollback();

                           e.printStackTrace();

                           logger.info("Error en la clase: " + this.getClass().getName() + " - " + e.getMessage());

                     finally 

                           session.close();

                    

              else 

                    try 

                           for (Iterator iterator = entity.iterator(); iterator.hasNext();) 

                                  T t = (T) iterator.next();

                                  if ( update ) 

                                        session.saveOrUpdate(t);

                                   else 

                                        session.save(t);   

                                  

                           

                           return true;

                     catch (Exception e) 

                           e.printStackTrace();

                           logger.info("Error en la clase: " + this.getClass().getName() + " - " + e.getMessage());

                    

             



             return false;

       



       public SessionFactory getSessionFactory() 

             return sessionFactory;

       



       @Transactional

       public void flush() throws DataAccessException 

             sessionFactory.getCurrentSession().flush();

       




有人可以帮助理解为什么当对象用户在 save() 中使用时出现此错误。

谢谢。

【问题讨论】:

你正在混合容器管理事务和 bean 管理事务,它不会工作。既然你用的是spring,可以跟着教程spring.io/guides/gs/accessing-data-jpa @André 对不起,我是网络开发的新手,我发现你的回答真的很混乱 您没有让 Spring 为您管理事务。您只需要@Autowired@Transaction。该教程是您需要的一切。刮掉所有内容并阅读有关 Spring JPA 的其他一些教程,直到您掌握了窍门。让您的代码工作不会走得太远。 @André 谢谢,我会检查你的链接,我错过了很多概念,这不会让我完成我的工作。 【参考方案1】:

确保容器创建 dao 对象 bean 并注入您的服务类 尝试关注--

确保您在标签/注释之后添加了 spring 配置文件/类--

 @ComponentScan(BasePackages="fully Qualified dao class name")

&lt;context:component-scan="fully Qualified dao class name"&gt;

【讨论】:

嗨,我的上下文:component-scan 有我认为正确的项目主文件夹吗?谢谢 确保您在 dao 类中使用了 '@repository' 或 '@component' 注释【参考方案2】:

感谢大家的帮助,我的休眠会话 bean 声明中有一个错误

【讨论】:

以上是关于NullPointerException 使用 Spring 使 Generic Dao 休眠的主要内容,如果未能解决你的问题,请参考以下文章

java.lang.NullPointerException 是使用方法引用而不是 lambda 表达式引发的

来自 Google 地图的 NullPointerException

NullPointerException 而不是 null(JVM 错误?)

Broadleaf电商平台上传图片出现NullPointerException

尝试将列表转换回数组时出现 NullPointerException

java解析文件jsoup报错java.lang.NullPointerException,求解决方案!