虽然持久化框架自己用的比较多,比如mybatis,jpa,或者apache的Dbutil,在这里,把自己使用hibernate常用的方法记录下来,方便以后使用。
每个人使用hibernate都有自己的见解,我的一般做法是,使用数据库(在这里使用mysql)建表,然后使用myeclipse9或者更高版本的hibernate java类生成工具,生成注解的bean,然后让生成的bean继承自己写的BaseBean类。
自己通用的BaseBean
import java.io.Serializable;
import org.apache.commons.lang3.builder.ToStringBuilder;
/**
* 通用bean
* @author xiaoliouc
*
*/
public class BaseBean implements Serializable {
public String toString()
{
return ToStringBuilder.reflectionToString(this);
}
}
自己使用hibernate通用的dao
import java.io.Serializable;
import java.lang.reflect.ParameterizedType;
import java.util.List;
import org.hibernate.Query;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.springframework.beans.factory.annotation.Autowired;
import com.nfs.common.page.PageBean;
/**
* BaseDao 定义DAO的通用操作的实现
* @author xiaoliouc
*/
@SuppressWarnings("unchecked")
public class BaseDao<T> {
private Class<T> clazz;
/**
* 通过构造方法指定DAO的具体实现类
*/
public BaseDao() {
ParameterizedType type = (ParameterizedType) this.getClass().getGenericSuperclass();
clazz = (Class<T>) type.getActualTypeArguments()[0];
// System.out.println("DAO的真实实现类是:" + this.clazz.getName());
}
@Autowired
private SessionFactory sessionFactory;
public Session getSession() {
//事务必须是开启的(Required),否则获取不到
return sessionFactory.getCurrentSession();
}
public void save(T entity) {
this.getSession().save(entity);
}
public void update(T entity) {
this.getSession().update(entity);
}
public void delete(Serializable id) {
this.getSession().delete(this.get(id));
}
public T get(Serializable id) {
return (T) this.getSession().get(this.clazz, id);
}
public List<T> findByHQL(String hql, Object[] params) {
Query query = this.getSession().createQuery(hql);
for (int i = 0; params != null && i < params.length; i++) {
query.setParameter(i, params[i]);
}
return query.list();
}
public int getAllRowCount(String hql , final Object[] params ){
Query query = getSession().createQuery(hql.toString());
for (int i = 0; params != null && i < params.length; i++)
{
query.setParameter( i , params[i]);
}
return query.list().size();
}
/**
* 使用hql 语句进行分页查询操作
* @param hql 需要查询的hql语句
* @param values 如果hql有多个个参数需要传入,values就是传入的参数数组
* @param offset 第一条记录索引
* @param pageSize 每页需要显示的记录数
* @return 当前页的所有记录
*/
public List<T> queryForPage(final String hql, final Object[] params ,final int offset,final int length){
Query query = getSession().createQuery(hql);
for (int i = 0; params != null && i < params.length; i++)
{
query.setParameter( i , params[i]);
}
query.setFirstResult(offset);
query.setMaxResults(length);
List<T> list = query.list();
return list;
}
public PageBean findForPage(String hql , final Object[] values, int pageSize,int page){
int allRow = getAllRowCount(hql,values); //总记录数
int totalPage = PageBean.countTotalPage(pageSize, allRow); //总页数
final int currentPage = PageBean.countCurrentPage(page);
final int offset = PageBean.countOffset(pageSize, currentPage); //当前页开始记录
final int length = pageSize; //每页记录数
List<T> list = queryForPage(hql,values,offset, length);
//把分页信息保存到Bean中
PageBean pageBean = new PageBean();
pageBean.setPageSize(pageSize);
pageBean.setCurrentPage(currentPage);
pageBean.setAllRow(allRow);
pageBean.setTotalPage(totalPage);
pageBean.setList(list);
pageBean.init();
return pageBean;
}
}
import java.util.*;
//通用分页
public class PageBean {
private List list; //要返回的某一页的记录列表
private int allRow; //总记录数
private int totalPage; //总页数
private int currentPage; //当前页
private int pageSize; //每页记录数
private boolean isFirstPage; //是否为第一页
private boolean isLastPage; //是否为最后一页
private boolean hasPreviousPage; //是否有前一页
private boolean hasNextPage; //是否有下一页
public List getList() {
return list;
}
public void setList(List list) {
this.list = list;
}
public int getAllRow() {
return allRow;
}
public void setAllRow(int allRow) {
this.allRow = allRow;
}
public int getTotalPage() {
return totalPage;
}
public void setTotalPage(int totalPage) {
this.totalPage = totalPage;
}
public int getCurrentPage() {
return currentPage;
}
public void setCurrentPage(int currentPage) {
this.currentPage = currentPage;
}
public int getPageSize() {
return pageSize;
}
public void setPageSize(int pageSize) {
this.pageSize = pageSize;
}
/** *//**
* 初始化分页信息
*/
public void init(){
this.isFirstPage = isFirstPage();
this.isLastPage = isLastPage();
this.hasPreviousPage = isHasPreviousPage();
this.hasNextPage = isHasNextPage();
}
/** *//**
* 以下判断页的信息,只需getter方法(is方法)即可
* @return
*/
public boolean isFirstPage() {
return currentPage == 1; // 如是当前页是第1页
}
public boolean isLastPage() {
return currentPage == totalPage; //如果当前页是最后一页
}
public boolean isHasPreviousPage() {
return currentPage != 1; //只要当前页不是第1页
}
public boolean isHasNextPage() {
return currentPage != totalPage; //只要当前页不是最后1页
}
/** *//**
* 计算总页数,静态方法,供外部直接通过类名调用
* @param pageSize 每页记录数
* @param allRow 总记录数
* @return 总页数
*/
public static int countTotalPage(final int pageSize,final int allRow){
int totalPage = allRow % pageSize == 0 ? allRow/pageSize : allRow/pageSize+1;
return totalPage;
}
/** *//**
* 计算当前页开始记录
* @param pageSize 每页记录数
* @param currentPage 当前第几页
* @return 当前页开始记录号
*/
public static int countOffset(final int pageSize, int currentPage){
final int offset = pageSize*(currentPage-1);
return offset;
}
/** *//**
* 计算当前页,若为0或者请求的URL中没有"?page=",则用1代替
* @param page 传入的参数(可能为空,即0,则返回1)
* @return 当前页
*/
public static int countCurrentPage(int page){
final int curPage = (page==0?1:page);
return curPage;
}
}
使用方法:
以News为例,使用news生成News这个类,并让News继承BaseBean,
然后写一个
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.stereotype.Repository;
import com.lee.common.dao.BaseDao;
import com.lee.demo.bean.News;
@Repository("newsDao")
public class NewsDao extends BaseDao<News>{
@Autowired
@Qualifier("sessionFactory")
private SessionFactory sessionFactory;
public Session getSession() {
//事务必须是开启的(Required),否则获取不到
return sessionFactory.getCurrentSession();
}
/**
* 下面写通用dao里没实现的方法
*/
}
在service层中调用公用的方法就可以,其实基本上的功能都已经实现了,只需要在service层写hql语句,参数就可以了