最近在学习SSH,struts2.3+spring4+hibernate4,都是一些最基本的增删改查,总结了一些问题及解决的办法,如果有错误还请指教。
sessionFactory的配置:
1 <!-- 配置hibernate session工厂 -->
<!--hibernate4-->
<!-- <bean id="sessionFactory" class="org.springframework.orm.hibernate4.LocalSessionFactoryBean"> -->
<!--hibernate3-->
2 <bean id="sessionFactory" class="org.springframework.orm.hibernate3.annotation.AnnotationSessionFactoryBean">
3 <property name="dataSource" ref="dataSource" />
4 <property name="hibernateProperties">
5 <props>
6 <prop key="hibernate.hbm2ddl.auto">${hibernate.hbm2ddl.auto}</prop>
7 <prop key="hibernate.dialect">${hibernate.dialect}</prop>
8 <prop key="hibernate.show_sql">${hibernate.show_sql}</prop>
9 <prop key="hibernate.format_sql">${hibernate.format_sql}</prop>
10 </props>
11 </property>
13 <!-- 自动扫描注解方式配置的hibernate类文件 -->
14 <property name="packagesToScan">
15 <list>
16 <value>com.huxin.model</value>
17 </list>
18 </property>
23 </bean>
因为Spring3.1以上版本不再为hibernate提供HibernateTemplate这个类,因此我用的hibernate原生的session:
公共接口:
/**
* @author HuXin
* @param <T> 公共接口 因此加了范型
*/
public interface BaseDao<T> {
public void save(T t);
public void delete(T t);
public void deleteById(String hql,Integer id);
public void update(T t);
public void saveOrUpdate(T o);
//单一查
public T get(Class<T> c, Serializable id);
//查询总条数
public Long count(String hql);
//全查
public List<T> find(String hql);
//分页
public List<T> find(String hql,int pageNo,int pageSize);
//用作批量删除
public int executeHql(String hql);
公共接口的实现类:
package com.huxin.DaoImpl;
import java.io.Serializable;
import java.util.List;
import java.util.Map;
import org.hibernate.Query;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;
import com.huxin.dao.BaseDao;
import com.huxin.model.SshEmployee;
@Repository("baseDao")
public class BaseDaoImpl<T> implements BaseDao<T> {
@Autowired
private SessionFactory sessionfactory;
//把获得session提出来 ,避免代码重复
private Session getCurrentSession() {
return this.sessionfactory.getCurrentSession();
}
//-------------------------------------------------------
@Override
public void save(T t) {
this.getCurrentSession().save(t);
}
@Override
public void delete(T t) {
this.getCurrentSession().delete(t);
}
@Override
public void deleteById(String hql,Integer id) {
Query query = this.getCurrentSession().createQuery(hql);
if (id != null) {
query.setInteger(0, id);
query.executeUpdate();
}
}
@Override
public void update(T t) {
this.getCurrentSession().update(t);
}
@Override
public void saveOrUpdate(T t) {
this.getCurrentSession().saveOrUpdate(t);
}
@Override
public T get(Class<T> c, Serializable id) {
return (T) this.getCurrentSession().get(c, id);
}
@Override
public Long count(String hql) {
Query query = this.getCurrentSession().createQuery(hql);
return (Long) query.uniqueResult();
}
@Override
public List<T> find(String hql) {
return this.getCurrentSession().createQuery(hql).list();
}
@Override
public List<T> find(String hql,int pageNo,int pageSize) {
Query query = this.getCurrentSession().createQuery(hql);
return query.setFirstResult((pageNo-1)*pageSize).setMaxResults(pageSize).list();
}
@Override
public int executeHql(String hql) {
return this.getCurrentSession().createQuery(hql).executeUpdate();
}
}
使用hibernate原生的session,当需要访问懒加载的数据时在web.xml中还需要配置一个过滤器:openSessionInViewFilter
web.xml 中的配置。
<!-- openSessionInView配置 一定要在struts2的配置之前 --> <filter> <filter-name>openSessionInViewFilter</filter-name> <filter-class>org.springframework.orm.hibernate4.support.OpenSessionInViewFilter</filter-class> <init-param> <param-name>singleSession</param-name> <param-value>true</param-value> </init-param> </filter> <!-- Struts2配置 --> <filter> <filter-name>struts2</filter-name> <filter-class>org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter</filter-class> </filter> <filter-mapping> <filter-name>openSessionInViewFilter</filter-name> <url-pattern>*.action</url-pattern> </filter-mapping> <filter-mapping> <filter-name>struts2</filter-name> <url-pattern>*.action</url-pattern> </filter-mapping>
我发现配置openSessionInViewFilter ,启动后他默认是给没有配置事务边界的方法都默认为只读的,当增删改的时候回没效果,即控制台不报错,而数据库并没有被修改,我的解决是:
<!-- 配置事务管理器 --> <bean name="transactionManager" class="org.springframework.orm.hibernate4.HibernateTransactionManager"> <property name="sessionFactory" ref="sessionFactory"></property> </bean> <!-- 定义传播特性 --> <tx:advice id="txAdvice" transaction-manager="transactionManager"> <tx:attributes> <tx:method name="add*" propagation="REQUIRED" /> <tx:method name="get*" propagation="REQUIRED" read-only="true" /> <tx:method name="list*" propagation="REQUIRED" read-only="true" /> <tx:method name="delete*" propagation="REQUIRED" /> <tx:method name="update*" propagation="REQUIRED" /> <tx:method name="*" propagation="REQUIRED" read-only="false" /> </tx:attributes> </tx:advice> <!-- 关联 哪些类 那些包 那些方法需要配置事务 --> <aop:config> <aop:pointcut expression="execution(* com.huxin.service.impl.*.*(..))" id="mycut" /> <aop:advisor advice-ref="txAdvice" pointcut-ref="mycut" /> </aop:config>