Spring整合Hibernate時,getHibernateTemplate().find()拋出空指針異常,通常源於HibernateTemplate未正確注入、SessionFactory配置錯誤或事務邊界缺失。本文提供完整排查清單與修正方案。
java.lang.NullPointerException
at org.springframework.orm.hibernate3.HibernateTemplate.find(HibernateTemplate.java:...)
at com.xxx.dao.UserDaoImpl.findUsers(UserDaoImpl.java:XX)
<bean id="sessionFactory" class="org.springframework.orm.hibernate3.LocalSessionFactoryBean">
<property name="dataSource" ref="dataSource" />
<property name="hibernateProperties">
<props>
<prop key="hibernate.dialect">org.hibernate.dialect.MySQLDialect</prop>
<prop key="hibernate.show_sql">true</prop>
<prop key="hibernate.hbm2ddl.auto">update</prop>
</props>
</property>
<property name="mappingResources">
<list>
<value>com/xxx/entity/User.hbm.xml</value>
</list>
</property>
</bean>
確保dataSource、方言、映射文件路徑均正確。
方式一:繼承HibernateDaoSupport(舊版推薦)
public class UserDaoImpl extends HibernateDaoSupport {
public List findUsers() {
return getHibernateTemplate().find("from User");
}
}
Spring配置:
<bean id="userDao" class="com.xxx.dao.UserDaoImpl">
<property name="sessionFactory" ref="sessionFactory" />
</bean>
方式二:直接注入HibernateTemplate(推薦)
<bean id="hibernateTemplate" class="org.springframework.orm.hibernate3.HibernateTemplate">
<property name="sessionFactory" ref="sessionFactory" />
</bean>
<bean id="userDao" class="com.xxx.dao.UserDaoImpl">
<property name="hibernateTemplate" ref="hibernateTemplate" />
</bean>
DAO中聲明private HibernateTemplate hibernateTemplate;及setter。
無事務時,HibernateTemplate每次操作都會開啟關閉Session,導致懶加載失效、實體遊離。需配置聲明式事務:
<tx:annotation-driven transaction-manager="txManager" />
<bean id="txManager" class="org.springframework.orm.hibernate3.HibernateTransactionManager">
<property name="sessionFactory" ref="sessionFactory" />
</bean>
Service層方法添加@Transactional註解。
確保.hbm.xml或註解映射正確,特別是many-to-one、set關聯的column、class屬性。示例中UserInfo、Event、Event_Grade三表關聯需驗證外鍵USERID、GRADE一致性。
新項目建議直接使用JpaRepository,無需手寫DAO、HibernateTemplate,自動提供findAll()、分頁、排序等功能:
public interface UserRepository extends JpaRepository {
List findByName(String name);
}