七、hibernate中的持久層模板操作HibernateTemplate的用法

利用模板操作來替換掉持久層的session,必須先將spring和hibernate之間進行整合,整合的applicationContext配置文件介紹在:

https://blog.csdn.net/IT_CREATE/article/details/86141823

 

那麼在持久層的代碼就如下面這樣寫:

1、對於增刪改(和session的操作差不多,也有save、update、delete三個方法)

@Repository
public class UserDaoImpl implements IUserDao {

	@Resource
	private HibernateTemplate hibernateTemplate;

	@Override
	public void saveUserBean(UserBean user) {
		// TODO Auto-generated method stub
		hibernateTemplate.save(user);
	}

	@Override
	public void updateUserBean(UserBean user) {
		// TODO Auto-generated method stub
		hibernateTemplate.update(user);
	}

	@Override
	public void deleteUserBean(UserBean user) {
		// TODO Auto-generated method stub
		hibernateTemplate.delete(user);
	}
}

2、對於查詢(通過id查詢數據也有get和load兩個方法)

@Repository
public class UserDaoImpl implements IUserDao {

	@Resource
	private HibernateTemplate hibernateTemplate;

	@Override
	public UserBean getUserBeanById(int id) {
		// TODO Auto-generated method stub
		return (UserBean) hibernateTemplate.get(UserBean.class, id);
	}

	@Override
	public UserBean loadUserBeanById(int id) {
		// TODO Auto-generated method stub
		/*
		 * get()和load()的區別: get()在查詢對象時,採用的是即時查詢方法,它從一級緩存開始,進行二級緩存,到達數據庫,它一定會得到一個最終的結果。
		 * load()在查詢對象時,採用的是延遲查詢方法,它從一級緩存開始,進行二級緩存,如果二級緩存中沒有對應的數據,它將默認數據庫中一定存在那條數據,
		 * 並返回該對象的代理對象, 直到程序發生調用時,纔去查詢,找到了就正常返回,找不到,拋異常:ObjectNotFoundException
		 */

		// 延遲加載對象,一定不能關閉Session
		return (UserBean) hibernateTemplate.load(UserBean.class, id);
	}
}

 

下面是自定義查詢條件:(具體的查詢方法可參考https://www.cnblogs.com/xrab/p/5586775.html

1、利用hql語句進行查詢的一些方法

@Repository
public class UserDaoImpl implements IUserDao {

	@Resource
	private HibernateTemplate hibernateTemplate;


	@Override
	public Map<String, Object> queryUserBeanById(Integer id) {
		// TODO Auto-generated method stub
		String hql = "select new map(u.userName as userName,u.loginName as loginName,u.password as password) From UserBean as u where id = ?";
		List<?> datas = hibernateTemplate.find(hql, new Object[] {id});
		if (datas != null)
			return (Map<String, Object>) datas.get(0);
		return null;
	}

	@Override
	public List<?> findUserBeanMapByObject(UserBean user) {
		// TODO Auto-generated method stub
		String hql = "select new map(u.loginName,u.userName,u.age) From UserBean as u where u.userName like concat(:userName,'%') and u.gender = :gender";
		//要求user對象的屬性,必須包含HQL中參數名稱,“:”後面的名稱必須和對象屬性一致
		return hibernateTemplate.findByValueBean(hql, user);
	}

	@Override
	public UserBean findUserBeanByLoginNameAndPwd(String loginName, String pwd) {
		// TODO Auto-generated method stub
		/*按照位置進行設值 */
//		  String hql = "From UserBean as u where u.loginName = ? and u.password = ?";
//		  List<?> datas = hibernateTemplate.find(hql, new Object[] {loginName,pwd});
//			if (datas != null) {
//				return (UserBean) datas.get(0);
//			}
//		  return null;
		

		/*
		 * 按照參數別名進行設值
		 */
		String hql = "From UserBean as u where u.loginName = :ln and u.password = :pwd";
		List<?> datas = hibernateTemplate.findByNamedParam(hql, new String[] {"ln","pwd"},new Object[] {loginName,pwd});
		if (datas != null)
			return (UserBean) datas.get(0);
		return null;
	}

	@Override
	public List<?> findUserBeanByObject(UserBean user) {
		// TODO Auto-generated method stub

		// --------------------------------------------------------
		// ----------使用Query完成多條件查詢(明顯的缺陷:需要拼接語句)--------
		// --------------------------------------------------------
		/*
		 * 
		 * */
		//select 字段列表 from 表 where 條件 
		String hql = "select new UserBean(u.loginName,u.userName,u.age) From UserBean as u where u.userName like concat(:userName,'%') and u.gender = :gender";
		return hibernateTemplate.findByValueBean(hql, user);
		
		 
		String hql = "select new map(u.loginName as loginName,u.userName as userName,u.age as age) From UserBean as u where u.userName like concat(:userName,'%') and u.gender = :gender";
		return hibernateTemplate.findByValueBean(hql, user);	 
	}

	/**
	 *通過Map查詢用戶數據方法
	 *如果傳入的是map,那麼map中鍵的名字必須和hql語句中“:參數名”的參數名一致,才能在預編譯後賦值生效。在這裏,也就是說,map中有兩個鍵,userName和gender
	 */
	@Override
	public List<?> findUserBeanByMap(Map map) {
		// TODO Auto-generated method stub
		String hql = "select new map(u.loginName as loginName,u.userName as userName,u.age as age) From UserBean as u where u.userName like concat(:userName,'%') and u.gender = :gender";
		return hibernateTemplate.findByValueBean(hql, map);
	}

	/**
	 *得到分頁數據方法
	 */
	@SuppressWarnings("all")
	@Override
	public PageBean findUserBeanList2PageBean(PageBean page, UserBean user) {
	
		// --------------------------------------------------------
		// ----------使用Query完成多條件查詢(明顯的缺陷:需要拼接語句)--------
		// --------------------------------------------------------
		return (PageBean) hibernateTemplate.execute(new HibernateCallback() {

			@Override
			public Object doInHibernate(Session session) throws HibernateException {
				// TODO Auto-generated method stub
				  String hql = "select count(*) from UserBean as u where u.userName like concat(:userName,'%') and u.gender = :gender"; 
				  Query query = session.createQuery(hql); 
				  query.setProperties(user);
				  //uniqueResult()表示返回一個唯一的結果 
				  long totalRows = (long) query.uniqueResult();
				  
				  List<?> datas = null; 
				  if(totalRows > 0) { 
					  hql = "from UserBean as u where u.userName like concat(:userName,'%') and u.gender = :gender"; 
					  query = session.createQuery(hql); 
					  query.setProperties(user);
				  
				  //設置數據庫中查詢起始位置、獲取的數據條數 
				  query.setFirstResult(page.getIndex());
				  query.setMaxResults(page.getRows()); 
				  datas = query.list(); 
				  
				  }
				  page.setTotalRows(totalRows); 
				  page.setData(datas); 
				  return page;
			}
			
		});
	}

}

利用hibernateTemplate.execute方法可以直接操作session,方法內部用到了匿名內部類,這樣就和直接操作session一樣了。上面的到分頁數據中的方法用到的PageBean類在文章尾部。

 

2、利用Criteria進行查詢的方法

@Repository
public class UserDaoImpl implements IUserDao {

	@Resource
	private HibernateTemplate hibernateTemplate;

	@Override
	public List<?> findUserBeanByObject(UserBean user) {
		// TODO Auto-generated method stub
		// --------------------------------------------------------
		// --------------使用Criteria完成多條件查詢---------------------
		// --------------------------------------------------------
		DetachedCriteria criteria = DetachedCriteria.forClass(UserBean.class);// From UserBean where 1=1
		if (!StringUtils.isEmpty(user.getLoginName())) {
			criteria.add(Restrictions.eq("loginName", user.getLoginName()));// and loginName = '"+user.getLoginName()+"'
		}
		if (!StringUtils.isEmpty(user.getUserName())) {
			criteria.add(Restrictions.like("userName", user.getUserName(), MatchMode.START));// and userName like
		}

		criteria.add(Restrictions.or(Restrictions.eq("gender", 0), Restrictions.eq("gender", 1)));

		criteria.add(Restrictions.between("age", 18, 60));// between …… and ……

		criteria.addOrder(Order.desc("createTime"));// 按照創建時間降序排列
		return hibernateTemplate.findByCriteria(criteria);	 
	}


	@SuppressWarnings("all")
	@Override
	public PageBean findUserBeanList2PageBean(PageBean page, UserBean user) {
		// TODO Auto-generated method stub
		// --------------------------------------------------------
		// --------------使用Criteria完成多條件查詢---------------------
		// --------------------------------------------------------
		
		return (PageBean) hibernateTemplate.execute(new HibernateCallback() {

			@Override
			public Object doInHibernate(Session session) throws HibernateException {
				// TODO Auto-generated method stub
				Criteria criteria = session.createCriteria(UserBean.class);
				if (!StringUtils.isEmpty(user.getLoginName())) {
					criteria.add(Restrictions.eq("loginName", user.getLoginName()));// and loginName = '"+user.getLoginName()+"'
				}
				if (!StringUtils.isEmpty(user.getUserName())) {
					criteria.add(Restrictions.like("userName", user.getUserName(), MatchMode.START));// and userName like
				}
				if (user.getGender() != null) {
					criteria.add(Restrictions.eq("gender", user.getGender()));
				}
				if (user.getBirthday() != null) {
					criteria.add(Restrictions.ge("birthday", user.getBirthday()));
				}

				// 添加投影
				criteria.setProjection(Projections.rowCount());// 我在From UserBean之上 添加了一個select count(*)
				
				long totalRows = (long) criteria.uniqueResult();// 獲得多少條
				List<?> datas = null;
				if (totalRows > 0) {
					// 去掉投影
					criteria.setProjection(null);
					criteria.setFirstResult(page.getIndex());
					criteria.setMaxResults(page.getRows());
					datas = criteria.list();
				}
				page.setTotalRows(totalRows);
				page.setData(datas);
				return page;
			}
		});
	}

	@Override
	public List<?> findUserBeanByIdcardAndAddress(String idcard, String address) {
		// TODO Auto-generated method stub
		
		// --------------------------------------------------------
		// --------------使用Criteria完成多條件查詢---------------------
		// --------------------------------------------------------
		DetachedCriteria criteria = DetachedCriteria.forClass(UserBean.class);//From UserBean as u where 1=1
		//關聯對象查詢,給關聯對象取別名,並且完成兩個對象之間的關聯
		criteria.createAlias("userInfo", "i",JoinType.LEFT_OUTER_JOIN);
		criteria.createAlias("adds", "a",JoinType.LEFT_OUTER_JOIN);
		
		if(!StringUtils.isEmpty(idcard)) {
			criteria.add(Restrictions.like("i.idcard", idcard,MatchMode.START));
		}
		if(!StringUtils.isEmpty(address)) {
			criteria.add(Restrictions.like("a.address", address,MatchMode.START));
		}
		
		return hibernateTemplate.findByCriteria(criteria);
	}

}

上面代碼中的findUserBeanByObject() findUserBeanByIdcardAndAddress()方法中用到了DetachedCriteria類,因爲hibernateTemplate.findByCriteria(DetachedCriteria  criteria)方法必須傳入DetachedCriteria,

關於DetachedCriteria和Criteria的區別自行查閱。他們的用法差不多,只是DetachedCriteria相比Criteria少了一些方法。

Criteria由session的createCriteria(類.class)方法產生,

DetachedCriteria由它自帶的2個靜態方法forClass(Class) 或 forEntityName(Name) 進行DetachedCriteria 的實例創建。

 

  • DetachedCriteria中去重複,並且將關聯對象裝配到主對象,用:  criteria.setResultTransformer(Criteria.DISTINCT_ROOT_ENTITY)
@Override
public List<?> findTeacherBeanByStudentName(String stuName) {
	// TODO Auto-generated method stub
//	String hql = "select DISTINCT(t) From TeacherBean as t left join fetch t.stus as s where s.stuName like concat(:stuName,'%')";
//	return hibernateTemplate.findByNamedParam(hql, "stuName", stuName);
		
		
	DetachedCriteria criteria = DetachedCriteria.forClass(TeacherBean.class);
	criteria.createAlias("stus", "s",JoinType.LEFT_OUTER_JOIN);
	if(!StringUtils.isEmpty(stuName)) {
		criteria.add(Restrictions.like("s.stuName", stuName, MatchMode.START));
	}
		
	//去重複,並且將關聯對象,裝配到主對象身上去,相當於hql與劇中的DISTINCT()加上fetch的作用
	criteria.setResultTransformer(Criteria.DISTINCT_ROOT_ENTITY);
	return hibernateTemplate.findByCriteria(criteria);
	
}

 

 

下面簡單列舉兩個返回分頁數據的例子:

1、利用Criteria

@Repository
public class StudentDaoImpl implements IStudentDao {

	@Resource
	private HibernateTemplate hibernateTemplate;

	@SuppressWarnings("all")
	@Override
	public void findStudentBeanByTeacherName2PageBean(PageBean page, String teacherName) {
		// TODO Auto-generated method stub
		
		hibernateTemplate.execute(new HibernateCallback() {

			@Override
			public Object doInHibernate(Session session) throws HibernateException {
				// TODO Auto-generated method stub
				Criteria criteria = session.createCriteria(StudentBean.class);
				criteria.createAlias("teacher", "t",JoinType.LEFT_OUTER_JOIN);
				if(!StringUtils.isEmpty(teacherName)) {
					criteria.add(Restrictions.like("t.teacherName", teacherName, MatchMode.START));
				}
				
				//添加投影
				criteria.setProjection(Projections.rowCount());
				long totalRows = (long) criteria.uniqueResult();
				List<?> datas = null;
				if(totalRows > 0) {
					criteria.setProjection(null);
					criteria.setFirstResult(page.getIndex());
					criteria.setMaxResults(page.getRows());
					criteria.setResultTransformer(Criteria.ROOT_ENTITY);//這句話的作用  === HQL中編寫的fetch
					datas = criteria.list();
				}
				page.setTotalRows(totalRows);
				page.setData(datas);
				return page;
			}
		});
	}

}

2、利用hql

@Repository
public class StudentDaoImpl implements IStudentDao {

	@Resource
	private HibernateTemplate hibernateTemplate;

	@SuppressWarnings("all")
	@Override
	public void findStudentBeanByTeacherName2PageBean(PageBean page, String teacherName) {
		// TODO Auto-generated method stub
		
		
		hibernateTemplate.execute(new HibernateCallback() {

			@Override
			public Object doInHibernate(Session session) throws HibernateException {
				// TODO Auto-generated method stub
				String hql = "select count(*) From StudentBean as s left join s.teacher as t where t.teacherName like concat(:teacherName,'%')";
				Query query = session.createQuery(hql);
				query.setString("teacherName", teacherName);
				long totalRows = (long) query.uniqueResult();
				List<?> datas = null;
				if(totalRows > 0) {
					hql = "From StudentBean as s left join fetch s.teacher as t where t.teacherName like concat(:teacherName,'%')";
					query = session.createQuery(hql);
					query.setString("teacherName", teacherName);
					query.setFirstResult(page.getIndex());
					query.setMaxResults(page.getRows());
					datas = query.list();
				}
				page.setTotalRows(totalRows);
				page.setData(datas);
				return page;
			}
		});
		
	}

}

 

PageBean類:

package com.ge.hibernatexml.bean;

import java.util.List;

/**
 * 分頁對象
 * @author Administrator
 *
 */
public class PageBean {

	private int page;//當前頁碼
	private int rows;//每頁顯示數據的行數
	
	private int index;//數據獲取的起始位置(數據庫中)
	private long totalRows;//數據總條數
	private long totalPage;//總共有多少頁
	
	private String sort;//排序字段
	private String order;//排序方式
	
	//具體的數據
	private List<?> data;

	
	public PageBean() {
		super();
		// TODO Auto-generated constructor stub
	}
	
	public PageBean(int page, int rows) {
		super();
		this.page = page;
		this.rows = rows;
		//計算數據獲取的起始位置
		this.index = (page - 1) * rows;
	}


	public int getPage() {
		return page;
	}

	public void setPage(int page) {
		this.page = page;
	}

	public int getRows() {
		return rows;
	}

	public void setRows(int rows) {
		this.rows = rows;
	}

	public int getIndex() {
		return index;
	}

	public void setIndex(int index) {
		this.index = index;
	}

	public long getTotalRows() {
		return totalRows;
	}

	public void setTotalRows(long totalRows) {
		this.totalRows = totalRows;
		//總頁碼
		this.totalPage = totalRows % rows == 0 ? totalRows / rows : totalRows / rows + 1;
	}

	public String getSort() {
		return sort;
	}

	public void setSort(String sort) {
		this.sort = sort;
	}

	public String getOrder() {
		return order;
	}

	public void setOrder(String order) {
		this.order = order;
	}

	public long getTotalPage() {
		return totalPage;
	}

	public void setTotalPage(long totalPage) {
		this.totalPage = totalPage;
	}

	public List<?> getData() {
		return data;
	}

	public void setData(List<?> data) {
		this.data = data;
	}

	@Override
	public String toString() {
		return "PageBean [page=" + page + ", rows=" + rows + ", index=" + index + ", totalRows=" + totalRows
				+ ", totalPage=" + totalPage + ", sort=" + sort + ", order=" + order + ", data=" + data + "]";
	}
}

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章