重新对springboot进行了封装,主要有以下内容:
1、对JpaRepository进行了自定义扩展,业务类的所有数据库访问接口继承BaseDaoIF
BaseBaoFactoryBean.java
package com.mm.happy.dao;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.support.JpaRepositoryFactory;
import org.springframework.data.jpa.repository.support.JpaRepositoryFactoryBean;
import org.springframework.data.repository.core.RepositoryInformation;
import org.springframework.data.repository.core.RepositoryMetadata;
import org.springframework.data.repository.core.support.RepositoryFactorySupport;
import javax.persistence.EntityManager;
import java.io.Serializable;
@SuppressWarnings({ "rawtypes", "unchecked" })
public class BaseBaoFactoryBean, T, I extends Serializable> extends JpaRepositoryFactoryBean {
public BaseBaoFactoryBean(Class extends R> repositoryInterface) {
super(repositoryInterface);
}
@Override
protected RepositoryFactorySupport createRepositoryFactory(EntityManager em) {
return new BaseRepositoryFactory(em);
}
// 创建一个内部类,该类不用在外部访问
private static class BaseRepositoryFactory extends JpaRepositoryFactory {
private final EntityManager em;
public BaseRepositoryFactory(EntityManager em) {
super(em);
this.em = em;
}
// 设置具体的实现类是BaseRepositoryImple
@Override
protected Object getTargetRepository(RepositoryInformation information) {
return new BaseBaoImpl((Class) information.getDomainType(), em);
}
// 设置具体的实现类的class
@Override
protected Class> getRepositoryBaseClass(RepositoryMetadata metadata) {
return BaseBaoImpl.class;
}
}
}
package com.mm.happy.dao;
import java.io.Serializable;
import java.lang.reflect.Field;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import javax.persistence.EntityManager;
import javax.persistence.Query;
import javax.persistence.criteria.CriteriaBuilder;
import javax.persistence.criteria.CriteriaQuery;
import javax.persistence.criteria.Predicate;
import javax.persistence.criteria.Root;
import org.springframework.data.jpa.domain.Specification;
import org.springframework.data.jpa.repository.support.SimpleJpaRepository;
import com.mm.happy.utils.StringUtil;
/**
*自定义扩展dao基类
*/
public class BaseBaoImpl extends SimpleJpaRepository implements BaseDaoIF {
private final EntityManager entityManager;
// 父类没有不带参数的构造方法,这里手动构造父类
public BaseBaoImpl(Class domainClass, EntityManager entityManager) {
super(domainClass, entityManager);
this.entityManager = entityManager;
}
// 通过EntityManager来完成查询
@SuppressWarnings("unchecked")
@Override
public List
BaseDaoIF.java
package com.mm.happy.dao;
import org.springframework.data.jpa.domain.Specification;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.JpaSpecificationExecutor;
import org.springframework.data.repository.NoRepositoryBean;
import org.springframework.transaction.annotation.Transactional;
import java.io.Serializable;
import java.util.List;
import java.util.Map;
/**
* dao扩展接口,子类接口需继承
* @author zbj
*
* @param
* @param
*/
@NoRepositoryBean
@Transactional(readOnly=true)
public interface BaseDaoIF extends JpaRepository,JpaSpecificationExecutor {
//sql语句查询
public List
1)前端配置,页面控件的名称以"search."打头,若是区间以"search.s."和“search.e.”打头
/**
* 组装查询条件
*/
@Override
public Specification buildSpecification(Map searchMap, Class domainClass) {
Specification specification = new Specification() {
@Override
public Predicate toPredicate(Root root, CriteriaQuery> query, CriteriaBuilder cb) {
// path转化
List predicates = new ArrayList<>();
try {
// 循环取出searchMap的值
Iterator> it = searchMap.entrySet().iterator();
while (it.hasNext()) {
Entry entry = it.next();
// 值
String value = entry.getValue()[0];
// 名称
String searchfiledName = entry.getKey();
// search.xxx转换成xxx, // 获取属性的名字
String name = null;
String values[] = null;
// 有区间的时候用"search.s."起始b,"search.e."结束标识
if (searchfiledName.startsWith("search.s.")) {
values = new String[2];
name = searchfiledName.substring(9);
values[0] = value;
if (searchMap.get("search.e." + name) != null) {
values[1] = searchMap.get("search.e." + name)[0];
}
} else if (searchfiledName.startsWith("search.e.")) {
continue;// 上面已经处理,这里直接跳过
} else {
if (!StringUtil.isNotBlank(value)) {
continue;// 不是区间范围的查询,值为空直接跳过
}
name = searchfiledName.substring(7);
}
Field field = domainClass.getDeclaredField(name);
// 获取属性类型
String type = field.getGenericType().toString();
// 获取查询字段的值,
if (type.equals("class java.lang.String")) {
if (values != null && values.length > 1) {
if (StringUtil.isNotBlank(values[0])) {
// 大于或等于传入值
predicates.add(cb.greaterThanOrEqualTo(root.get(name), values[0]));
}
if (values.length > 1 && StringUtil.isNotBlank(values[1])) {
// 小于或等于传入值
predicates.add(cb.lessThanOrEqualTo(root.get(name), values[1]));
}
} else {// 不是区间的情况
if (searchMap.get("search.equal." + name) != null) {// 配置了精确查询的情况
predicates.add(cb.equal(root.get(name), value));
} else {// 默认为模糊查询
predicates.add(cb.like(root.get(name), "%" + value + "%"));
}
}
} else if (type.equals("class java.util.Date")) {
if (values != null && values.length > 1) {
if (StringUtil.isNotBlank(values[0])) {
// 大于或等于传入时间
predicates.add(cb.greaterThanOrEqualTo(root.get(name).as(String.class), values[0]));
}
if (values.length > 1 && StringUtil.isNotBlank(values[1])) {
// 小于或等于传入时间
predicates.add(cb.lessThanOrEqualTo(root.get(name).as(String.class), values[1]));
}
} else {// 不是区间的情况
predicates.add(cb.equal(root.get(name).as(String.class), value));
}
} else {
if (values != null && values.length > 1) {
if (StringUtil.isNotBlank(values[0])) {
// 大于或等于传入值
predicates.add(cb.greaterThanOrEqualTo(root.get(name), values[0]));
}
if (values.length > 1 && StringUtil.isNotBlank(values[1])) {
// 小于或等于传入值
predicates.add(cb.lessThanOrEqualTo(root.get(name), values[1]));
}
} else {// 不是区间的情况
predicates.add(cb.equal(root.get(name).as(String.class), value));
}
}
}
} catch (Exception e) {
e.printStackTrace();
}
Predicate[] pre = new Predicate[predicates.size()];
return query.where(predicates.toArray(pre)).getRestriction();
}
};
return specification;
}
/**
* 分页获取列表用户数据
* @param request
* @param response
* @param searchCondition
* @return
*/
@ResponseBody
@RequestMapping(value = "get_users", method = RequestMethod.POST)
public ResponsePage findAll(HttpServletRequest req, HttpServletResponse res) {
// 初始化设置分页对象
ResponsePage userResp = initResponsePage(req, res);
// 查询条件设置
Specification specification = userDao.buildSpecification(getSearchFields(req), ExampleUser.class);
Page userPage = userDao.findAll(specification, new PageRequest(userResp.getPageNo() - 1, userResp.getPageSize(), userResp.getSort()));
// 查询后再补充设置分页对象
userResp = setResponsePage(userResp, userPage);
return userResp;
}