针对数据的增删改查,使用JPA做一些常用的封装。
一个基础DAO接口和一个DAO接口的实现类。
1、基础DAO接口BaseDao
package cn.luxh.app.dao.common; import java.util.List; import cn.luxh.app.util.Pagination; import cn.luxh.app.util.QueryCondition; /** * interface <code>BaseDao</code> DAO接口,封装常用的数据库操作 * * @author Luxh */ public interface BaseDao { /** * 新增实体 * @param entity 要新增的实体 */ public void save(Object entity); /** * 更新实体 * @param entity 要更新的实体 */ public void update(Object entity); /** * 根据主键删除实体 * @param <T> * @param clazz 实体类的Class * @param id 主键 */ public <T> void delete(Class<T> clazz,Object id); /** * 根据主键批量删除实体 * @param <T> * @param clazz 实体类的Class * @param id 主键数组 */ public <T> void delete(Class<T> clazz,Object[] ids); /** * 根据主键查询 * @param <T> * @param clazz 实体类的Class * @param id 主键 * @return */ public <T> T getById(Class<T> clazz,Object id); /** * 查询所有记录 * @param <T> * @param clazz 实体类的Class * @return */ public <T> List<T> getAll(Class<T> clazz); /** * 根据条件集合查询记录 * @param <T> * @param clazz * @param queryConditions 查询条件集合 * @param orderBy 排序,如 order by id desc * @param currentPage 当前页 * @param pageSize 每页显示记录数 * @return */ public <T> List<T> get(Class<T> clazz,List<QueryCondition> queryConditions,String orderBy,int currentPage,int pageSize); /** * 根据条件集合查询记录 * @param <T> * @param clazz * @param queryConditions 查询条件集合 * @return */ public <T> List<T> get(Class<T> clazz,List<QueryCondition> queryConditions); /** * 根据条件集合查询记录 * @param <T> * @param clazz * @param queryConditions 查询条件集合 * @param orderBy 排序,如 order by id desc * @return */ public <T> List<T> get(Class<T> clazz,List<QueryCondition> queryConditions,String orderBy); /** * 根据条件集合查询单条记录 * @param clazz * @param queryConditions 查询条件集合 * @return */ @SuppressWarnings("rawtypes") public Object getSingleResult(Class clazz,List<QueryCondition> queryConditions); /** * 根据条件查询记录数量 * @param clazz * @param queryConditions 查询条件集合 * @return */ @SuppressWarnings("rawtypes") public long getRecordCount(Class clazz,List<QueryCondition> queryConditions); /** * 根据jpql查询 * @param <T> * @param jpql * @param objects * @return */ public <T> List<T> getByJpql(String jpql,Object...objects); /** * 执行jpql语句 * @param jpql * @param objects * @return */ public int executeJpql(String jpql,Object...objects); /** * 分页查询 * @param <T> * @param clazz * @param queryConditions 查询条件集合 * @param orderBy 排序字段 如:order by id desc * @param currentPage 当前页 * @param pageSize 每页显示记录数 * @return */ public <T> Pagination<T> getPagination(Class<T> clazz,List<QueryCondition> queryConditions,String orderBy,int currentPage,int pageSize); /** * 查找唯一结果 * @param jpql * @param objects * @return */ public Object getUniqueResultByJpql(String jpql,Object...objects); }
2、DAO接口的实现类BaseDaoImpl
package cn.luxh.app.dao.common; import java.util.Iterator; import java.util.List; import javax.persistence.EntityManager; import javax.persistence.PersistenceContext; import javax.persistence.Query; import org.springframework.stereotype.Repository; import cn.luxh.app.util.Pagination; import cn.luxh.app.util.QueryCondition; /** * Class <code>BaseDaoImpl</code> DAO接口实现类,实现常用的操作 * * @author Luxh */ @Repository(value="baseDao") public class BaseDaoImpl implements BaseDao { @PersistenceContext protected EntityManager em; public <T> void delete(Class<T> clazz, Object id) { T entity = em.find(clazz, id); em.remove(entity); } public <T> void delete(Class<T> clazz, Object[] ids) { T entity = null; for(Object id : ids) { entity = em.find(clazz, id); em.remove(entity); } } @SuppressWarnings("unchecked") public <T> List<T> getAll(Class<T> clazz) { String className = clazz.getSimpleName(); StringBuffer jpql = new StringBuffer("select o from "); jpql.append(className).append(" o "); return em.createQuery(jpql.toString()).getResultList(); } public <T> T getById(Class<T> clazz, Object id) { return em.find(clazz, id); } public void save(Object entity) { em.persist(entity); } public void update(Object entity) { em.merge(entity); } @SuppressWarnings("unchecked") public <T> List<T> get(Class<T> clazz, List<QueryCondition> queryConditions,String orderBy,int currentPage,int pageSize) { Query query = getQuery(clazz, queryConditions, orderBy, false); if(currentPage == 0 && pageSize == 0) { return query.getResultList(); }else { return query.setFirstResult((currentPage-1)*pageSize).setMaxResults(pageSize).getResultList(); } } /** * 根据查询条件获取Query * @param clazz * @param queryConditions * @param orderBy * @param isQueryTotal 是否查询记录总数, true 则查询记录总数 * @return */ @SuppressWarnings("rawtypes") private Query getQuery(Class clazz, List<QueryCondition> queryConditions,String orderBy,boolean isQueryTotal) { String className = clazz.getSimpleName(); String preJPQL = isQueryTotal?"select count(*) from ":"select o from "; StringBuffer jpql = new StringBuffer(preJPQL); jpql.append(className).append(" o where 1=1 "); Query query = null; if(queryConditions != null && queryConditions.size() > 0) { //构造jpql语句 Iterator<QueryCondition> iterator = queryConditions.iterator(); while(iterator.hasNext()) { QueryCondition queryCondition = iterator.next(); if(queryCondition!=null) { if(queryCondition.getOperator().equals(QueryCondition.CUSTOM)) { jpql.append(" and (").append(queryCondition.getCustomJPQL()).append(")"); } if(queryCondition.getValue() != null && !"".equals(queryCondition.getValue())) { //如果占位符名称是*.*格式,则换成*_*格式。且:和名称之间不能有空格 String placeholder = queryCondition.getField().indexOf(".")!=-1 ? queryCondition.getField().replace(".", "_"):queryCondition.getField(); jpql.append(" and o.").append(queryCondition.getField().trim()) .append(" ").append(queryCondition.getOperator()).append(":").append(placeholder.trim()); } } } } if(orderBy != null && !"".equals(orderBy)) { jpql.append(" ").append(orderBy); } query = em.createQuery(jpql.toString()); if(queryConditions != null && queryConditions.size() > 0) { //为参数赋值 Iterator<QueryCondition> iterator2 = queryConditions.iterator(); while(iterator2.hasNext()) { QueryCondition queryCondition = iterator2.next(); if(queryCondition!=null) { if(queryCondition.getValue() != null && !"".equals(queryCondition.getValue())) { //将占位符中的.替换成_ queryCondition.setField(queryCondition.getField().indexOf(".") != -1 ? queryCondition.getField().replace(".", "_"):queryCondition.getField()); if(queryCondition.getOperator().equals(QueryCondition.LK)) { query.setParameter(queryCondition.getField(), "%"+queryCondition.getValue()+"%"); }else { query.setParameter(queryCondition.getField(), queryCondition.getValue()); } } } } } return query; } public <T> List<T> get(Class<T> clazz, List<QueryCondition> queryConditions) { return get(clazz, queryConditions, null, 0, 0); } public <T> List<T> get(Class<T> clazz, List<QueryCondition> queryConditions, String orderBy) { return get(clazz, queryConditions, orderBy, 0, 0); } @SuppressWarnings("rawtypes") public Object getSingleResult(Class clazz, List<QueryCondition> queryConditions) { Query query = getQuery(clazz, queryConditions, null, false); return query.getSingleResult(); } @SuppressWarnings("rawtypes") public long getRecordCount(Class clazz, List<QueryCondition> queryConditions) { Query query = getQuery(clazz, queryConditions, null, true); Object result = query.getSingleResult(); long recordCount = 0L; if(result != null) { recordCount = ((Long)result).longValue(); } return recordCount; } @SuppressWarnings("unchecked") public <T> List<T> getByJpql(String jpql, Object... objects) { Query query = em.createQuery(jpql); if(objects != null) { if (objects != null) { for(int i = 0 ; i < objects.length ; i ++){ query.setParameter(i, objects[i]); } } } return query.getResultList(); } public int executeJpql(String jpql,Object...objects) { Query query = em.createQuery(jpql); if (objects != null) { for(int i = 0 ; i < objects.length ; i ++){ query.setParameter(i, objects[i]); } } return query.executeUpdate(); } @SuppressWarnings({ "unchecked", "rawtypes" }) public <T> Pagination<T> getPagination(Class<T> clazz,List<QueryCondition> queryConditions,String orderBy,int currentPage,int pageSize) { List<T> recordList = get(clazz, queryConditions, orderBy, currentPage, pageSize); long recordCount = getRecordCount(clazz, queryConditions); return new Pagination(currentPage, pageSize, recordCount, recordList); } @Override public Object getUniqueResultByJpql(String jpql, Object... objects) { Query query = em.createQuery(jpql); if (objects != null) { for(int i = 0 ; i < objects.length ; i ++){ query.setParameter(i, objects[i]); } } return query.getSingleResult(); } }
3、查询条件工具类QueryCondition
package cn.luxh.app.util; /** * Class <code>QueryCondition</code> 查询条件 * @author Luxh */ public class QueryCondition { /**等于*/ public static final String EQ = "="; /**小于*/ public static final String LT = "<"; /**大于*/ public static final String GT = ">"; /**小于等于*/ public static final String LE = "<="; /**大于等于*/ public static final String GE = ">="; /**相似*/ public static final String LK = "like"; //可以再扩展 //...... /**自定义jpql语句*/ public static final String CUSTOM = "custom"; /**属性名*/ private String field; /**操作符*/ private String operator; /**值*/ private Object value; /**自定义jpql语句*/ private String customJPQL; /** * 传入自定义语句 * @param customJPQL */ public QueryCondition(String customJPQL) { this.customJPQL = customJPQL; this.operator = CUSTOM; } /** * * @param field 属性名 * @param operator 操作符 * @param value 值 如果属性是日期类型,需将字符串格式为日期 如new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").parse("2012-03-23 10:22:22") */ public QueryCondition(String field, String operator, Object value) { this.field = field; this.operator = operator; this.value = value; } public String getField() { return field; } public void setField(String field) { this.field = field; } public String getOperator() { return operator; } public void setOperator(String operator) { this.operator = operator; } public Object getValue() { return value; } public void setValue(Object value) { this.value = value; } public String getCustomJPQL() { return customJPQL; } public void setCustomJPQL(String customJPQL) { this.customJPQL = customJPQL; } }
4、查询条件QueryCondition的使用
List<QueryCondition> queryConditions = new ArrayList<QueryCondition>(); //根据姓名和年龄的范围查找用户 //对应的SQL: name = '楚留香' queryConditions.add(new QueryCondition("name",QueryCondition.EQ,"楚留香")); //对应的SQL: age = 10 or age =20 queryConditions.add(new QueryCondition("age = 10 or age =20")); List<User> users = baseDao.get(User.class, queryConditions);
5、分页工具类Pagination:http://www.cnblogs.com/luxh/archive/2012/08/11/2633844.html