HibernateBaseDao.java
package com.common.hibernate4;
/**
* Hibernate实现父子结构tree,使用The Nested Set Model算法
*/
public interface HibernateTree {
/**
* 默认树左边属性名称
*/
public static final String DEF_LEFT_NAME = "lft";
/**
* 默认树右边属性名称
*/
public static final String DEF_RIGHT_NAME = "rgt";
/**
* 默认父节点属性名称
*/
public static final String DEF_PARENT_NAME = "parent";
/**
* 实体类别名
*/
public static final String ENTITY_ALIAS = "bean";
/**
* 获得树左边属性名称
*
* @return
*/
public String getLftName();
/**
* 获得树右边属性名称
*
* @return
*/
public String getRgtName();
/**
* 获得父节点属性名称
*
* @return
*/
public String getParentName();
/**
* 获得树左边值
*
* @return
*/
public T getLft();
/**
* 设置树左边值
*
* @param lft
*/
public void setLft(T lft);
/**
* 获得树右边值
*
* @return
*/
public T getRgt();
/**
* 设置数右边值
*
* @param rgt
*/
public void setRgt(T rgt);
/**
* 获得父节点ID
*
* @return 如果没有父节点,则返回null。
*/
public T getParentId();
/**
* 获得树ID
*
* @return
*/
public T getId();
/**
* 获得附加条件
*
* 通过附加条件可以维护多棵树相互独立的树,附加条件使用hql语句,实体别名为bean。例如:bean.website.id=5
*
* @return 为null则不添加任何附加条件
* @see HibernateTree#ENTITY_ALIAS
*/
public String getTreeCondition();
}
package com.common.hibernate4;
import java.util.ArrayList;
import java.util.List;
import org.hibernate.Criteria;
import org.hibernate.Query;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.criterion.CriteriaSpecification;
import org.hibernate.criterion.Projection;
import org.hibernate.criterion.Projections;
import org.hibernate.internal.CriteriaImpl;
import org.hibernate.transform.ResultTransformer;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.util.Assert;
import com.jeecms.common.page.Pagination;
import com.jeecms.common.util.MyBeanUtils;
/**
* hibernate DAO基类
*
* 提供hql分页查询,不带泛型,与具体实体类无关。
*/
public abstract class HibernateSimpleDao {
/**
* 日志,可用于子类
*/
protected Logger log = LoggerFactory.getLogger(getClass());
/**
* HIBERNATE 的 order 属性
*/
protected static final String ORDER_ENTRIES = "orderEntries";
/**
* 通过HQL查询对象列表
*
* @param hql
* hql语句
* @param values
* 数量可变的参数
*/
@SuppressWarnings("unchecked")
protected List find(String hql, Object... values) {
return createQuery(hql, values).list();
}
/**
* 通过HQL查询唯一对象
*/
protected Object findUnique(String hql, Object... values) {
return createQuery(hql, values).uniqueResult();
}
/**
* 通过Finder获得分页数据
*
* @param finder
* Finder对象
* @param pageNo
* 页码
* @param pageSize
* 每页条数
* @return
*/
protected Pagination find(Finder finder, int pageNo, int pageSize) {
int totalCount = countQueryResult(finder);
Pagination p = new Pagination(pageNo, pageSize, totalCount);
if (totalCount < 1) {
p.setList(new ArrayList());
return p;
}
Query query = getSession().createQuery(finder.getOrigHql());
finder.setParamsToQuery(query);
query.setFirstResult(p.getFirstResult());
query.setMaxResults(p.getPageSize());
if (finder.isCacheable()) {
query.setCacheable(true);
}
List list = query.list();
p.setList(list);
return p;
}
protected Pagination findByGroup(Finder finder,String selectSql, int pageNo, int pageSize) {
return findByTotalCount(finder, pageNo, pageSize, countQueryResultByGroup(finder,selectSql));
}
/**
* 通过Finder获得列表数据
*
* @param finder
* @return
*/
@SuppressWarnings("unchecked")
protected List find(Finder finder) {
Query query = finder.createQuery(getSession());
List list = query.list();
return list;
}
/**
* 根据查询函数与参数列表创建Query对象,后续可进行更多处理,辅助函数.
*/
protected Query createQuery(String queryString, Object... values) {
Assert.hasText(queryString);
Query queryObject = getSession().createQuery(queryString);
if (values != null) {
for (int i = 0; i < values.length; i++) {
queryObject.setParameter(i, values[i]);
}
}
return queryObject;
}
/**
* 通过Criteria获得分页数据
*
* @param crit
* @param pageNo
* @param pageSize
* @param projection
* @param orders
* @return
*/
@SuppressWarnings("unchecked")
protected Pagination findByCriteria(Criteria crit, int pageNo, int pageSize) {
CriteriaImpl impl = (CriteriaImpl) crit;
// 先把Projection、ResultTransformer、OrderBy取出来,清空三者后再执行Count操作
Projection projection = impl.getProjection();
ResultTransformer transformer = impl.getResultTransformer();
List orderEntries;
try {
orderEntries = (List) MyBeanUtils
.getFieldValue(impl, ORDER_ENTRIES);
MyBeanUtils.setFieldValue(impl, ORDER_ENTRIES, new ArrayList());
} catch (Exception e) {
throw new RuntimeException(
"cannot read/write 'orderEntries' from CriteriaImpl", e);
}
int totalCount = ((Number) crit.setProjection(Projections.rowCount())
.uniqueResult()).intValue();
Pagination p = new Pagination(pageNo, pageSize, totalCount);
if (totalCount < 1) {
p.setList(new ArrayList());
return p;
}
// 将之前的Projection,ResultTransformer和OrderBy条件重新设回去
crit.setProjection(projection);
if (projection == null) {
crit.setResultTransformer(CriteriaSpecification.ROOT_ENTITY);
}
if (transformer != null) {
crit.setResultTransformer(transformer);
}
try {
MyBeanUtils.setFieldValue(impl, ORDER_ENTRIES, orderEntries);
} catch (Exception e) {
throw new RuntimeException(
"set 'orderEntries' to CriteriaImpl faild", e);
}
crit.setFirstResult(p.getFirstResult());
crit.setMaxResults(p.getPageSize());
p.setList(crit.list());
return p;
}
/**
* 获得Finder的记录总数
*
* @param finder
* @return
*/
protected int countQueryResult(Finder finder) {
Query query = getSession().createQuery(finder.getRowCountHql());
finder.setParamsToQuery(query);
if (finder.isCacheable()) {
query.setCacheable(true);
}
return ((Number) query.iterate().next()).intValue();
}
protected int countQueryResultByGroup(Finder finder,String selectSql) {
Query query = getSession().createQuery(finder.getRowCountTotalHql(selectSql));
setParamsToQuery(finder, query);
return ((Number) query.iterate().next()).intValue();
}
private Pagination findByTotalCount(Finder finder, int pageNo, int pageSize,int totalCount) {
Pagination p = new Pagination(pageNo, pageSize, totalCount);
if (totalCount < 1) {
p.setList(new ArrayList());
return p;
}
Query query = getSession().createQuery(finder.getOrigHql());
finder.setParamsToQuery(query);
query.setFirstResult(p.getFirstResult());
query.setMaxResults(p.getPageSize());
if (finder.isCacheable()) {
query.setCacheable(true);
}
List list = query.list();
p.setList(list);
return p;
}
private Query setParamsToQuery(Finder finder,Query query){
finder.setParamsToQuery(query);
if (finder.isCacheable()) {
query.setCacheable(true);
}
return query;
}
protected SessionFactory sessionFactory;
@Autowired
public void setSessionFactory(SessionFactory sessionFactory) {
this.sessionFactory = sessionFactory;
}
protected Session getSession() {
return sessionFactory.getCurrentSession();
}
}