标签:
做了一个Spring4和hibernate4的一个集成的例子,通过一个BasicHibernateDaoImpl.java构建基本的DAO处理类,代码片段如下:
1 package org.craig.dao.impl.base; 2 3 import java.io.Serializable; 4 import java.util.List; 5 import org.craig.dao.iface.base.IBasicDao; 6 import org.hibernate.Query; 7 import org.hibernate.Session; 8 import org.hibernate.SessionFactory; 9 10 public abstract class BasicHibernateDaoImpl<T> implements IBasicDao<T> { 11 // DAO组件进行持久化操作底层依赖的SessionFactory组件 12 private SessionFactory sessionFactory; 13 14 // 根据ID加载实体 15 @Override 16 @SuppressWarnings("unchecked") 17 public T get(Class<T> entityClazz, Serializable id) { 18 Session session = getSessionFactory().getCurrentSession(); 19 return (T) session.get(entityClazz, id); 20 } 21 22 // 保存实体 23 @Override 24 public Serializable save(T entity) { 25 return getSessionFactory().getCurrentSession().save(entity); 26 } 27 28 // 更新实体 29 @Override 30 public void update(T entity) { 31 getSessionFactory().getCurrentSession().saveOrUpdate(entity); 32 } 33 34 // 删除实体 35 @Override 36 public void delete(T entity) { 37 getSessionFactory().getCurrentSession().delete(entity); 38 } 39 40 // 根据ID删除实体 41 @Override 42 public void delete(Class<T> entityClazz, Serializable id) { 43 getSessionFactory() 44 .getCurrentSession() 45 .createQuery( 46 "delete " + entityClazz.getSimpleName() 47 + " en where en.id = ?0").setParameter("0", id) 48 .executeUpdate(); 49 } 50 51 // 获取所有实体 52 @Override 53 public List<T> findAll(Class<T> entityClazz) { 54 return find("select en from " + entityClazz.getSimpleName() + " en"); 55 }
在spring的配置中如下:
1 <bean id="abstractBasicDao" class="org.craig.dao.impl.base.BasicHibernateDaoImpl" abstract="true" 2 p:sessionFactory-ref="sessionFactory"/>
接着是员工DAO:
1 package org.craig.dao.impl; 2 3 import org.craig.dao.iface.IEmployeeDao; 4 import org.craig.dao.impl.base.BasicHibernateDaoImpl; 5 import org.craig.pojo.Employee; 6 7 public class EmployeeDaoImpl extends BasicHibernateDaoImpl<Employee> implements 8 IEmployeeDao { 9 10 }
在spring中的配置如下:
1 <bean id="employeeDao" parent="abstractBasicDao" class="org.craig.dao.impl.EmployeeDaoImpl"/>
接下来是spring和heibernate集成的配置
1 <bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource" 2 destroy-method="close" 3 p:driverClass="com.mysql.jdbc.Driver" 4 p:jdbcUrl="jdbc:mysql://localhost:3306/info" 5 p:user="root" 6 p:password="123456" 7 p:maxPoolSize="40" 8 p:minPoolSize="2" 9 p:initialPoolSize="2" 10 p:maxIdleTime="30" /> 11 <!-- 定义Hibernate的SessionFactory,SessionFactory需要依赖数据源,注入dataSource --> 12 <bean id="sessionFactory" 13 class="org.springframework.orm.hibernate4.LocalSessionFactoryBean" 14 p:dataSource-ref="dataSource"> 15 <property name="annotatedClasses"> 16 <list> 17 <value>org.craig.pojo.Employee</value> 18 </list> 19 </property> 20 <!-- 定义Hibernate SessionFactory的属性 --> 21 <property name="hibernateProperties"> 22 <props> 23 <!-- 指定Hibernate的连接方言 --> 24 <prop key="hibernate.dialect"> 25 org.hibernate.dialect.MySQL5Dialect</prop> 26 <prop key="hibernate.show_sql">true</prop> 27 <prop key="hibernate.format_sql">true</prop> 28 <prop key="hibernate.current_session_context_class">jta</prop> 29 30 <prop key="hibernate.connection.autocomit">false</prop> 31 32 </props> 33 </property> 34 </bean> 35 36 <!-- 增加事物 --> 37 <bean id="transactionManager" class="org.springframework.orm.hibernate4.LocalSessionFactoryBean" 38 p:sessionFactory-ref="sessionFactory"/> 39 40 <!-- AOP --> 41 <tx:advice id="txEmployee" transaction-manager="transactionManager"> 42 <tx:attributes> 43 <tx:method name="*" propagation="REQUIRED" /> 44 </tx:attributes> 45 </tx:advice> 46 47 <aop:config> 48 <aop:advisor advice-ref="txEmployee" pointcut="execution(* org.craig.dao.impl.*.*(..))"/> 49 </aop:config>
在登录的servlet代码中有如下操作:
1 IEmployeeDao employeeDao = SpringUtil.getBean("employeeDao", IEmployeeDao.class); 2 Employee emp = employeeDao.get(Employee.class, name);
这里的employeeDao.get()方法会调用BasicHibernateDaoImpl.java中的get(),在Session session = getSessionFactory().getCurrentSession();这里会报错误。错误代码如下:
1 严重: Servlet.service() for servlet login threw exception 2 org.hibernate.HibernateException: Unable to locate current JTA transaction 3 at org.hibernate.context.internal.JTASessionContext.currentSession(JTASessionContext.java:92) 4 at org.hibernate.internal.SessionFactoryImpl.getCurrentSession(SessionFactoryImpl.java:1014) 5 at org.craig.dao.impl.base.BasicHibernateDaoImpl.get(BasicHibernateDaoImpl.java:18) 6 at org.craig.manager.LoginServlet.doGet(LoginServlet.java:36) 7 at org.craig.manager.LoginServlet.doPost(LoginServlet.java:49) 8 at javax.servlet.http.HttpServlet.service(HttpServlet.java:710) 9 at javax.servlet.http.HttpServlet.service(HttpServlet.java:803) 10 at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290) 11 at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 12 at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:233) 13 at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:175) 14 at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:128) 15 at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102) 16 at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109) 17 at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:263) 18 at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:844) 19 at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:584) 20 at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:447) 21 at java.lang.Thread.run(Thread.java:662)
但是如果用SessionFactory.openSession()替换掉getCurrentSession()是可以获取到员工信息的。首先看了官方的说明,getCurrentSession()的前提是系统中拥有全局JTA事物,于是在tomcat中加入jotm的JTA事物管理,并且在启动时,控制台显示了JOTM TransactionManager的消息,并且在JSP页面也能通过代码获得UerTransaction,此时的transactionmanager的配置如下:
1 <bean id="transactionManager" class="org.springframework.transaction.jta.JtaTransactionManager"> 2 <property name="transactionSynchronizationRegistryName" value="java:comp/env/jta/jotmTransaction"></property> 3 <property name="transactionManagerName" value="java:comp/UserTransaction" /> 4 </bean>
但是依然报错,错误信息跟上面的一样。求高人指点!感谢了。
求解:SessionFactory.getCurrentSession()的异常问题
标签:
原文地址:http://www.cnblogs.com/craig-yilia/p/4683300.html