| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169 |
- package com.izouma.jmrh.web;
- import com.izouma.jmrh.annotations.Searchable;
- import com.izouma.jmrh.dto.PageQuery;
- import com.izouma.jmrh.utils.DateTimeUtils;
- import lombok.extern.slf4j.Slf4j;
- import org.apache.commons.lang3.StringUtils;
- import org.springframework.data.domain.PageRequest;
- import org.springframework.data.domain.Sort;
- import org.springframework.data.jpa.domain.Specification;
- import javax.persistence.criteria.Predicate;
- import java.lang.reflect.Field;
- import java.time.LocalDate;
- import java.time.LocalDateTime;
- import java.util.ArrayList;
- import java.util.Collection;
- import java.util.List;
- import java.util.regex.Pattern;
- @SuppressWarnings("ALL")
- @Slf4j
- public class BaseController {
- public PageRequest toPageRequest(PageQuery pageQuery) {
- PageRequest pageRequest;
- if (StringUtils.isNotEmpty(pageQuery.getSort())) {
- List<Sort.Order> orders = new ArrayList<>();
- for (String sortStr : pageQuery.getSort().split(";")) {
- String direction = "asc";
- String prop = sortStr;
- if (sortStr.contains(",asc") || sortStr.contains(",desc")) {
- prop = sortStr.split(",")[0];
- direction = sortStr.split(",")[1];
- }
- orders.add("asc".equals(direction) ? Sort.Order.asc(prop) : Sort.Order.desc(prop));
- }
- pageRequest = PageRequest.of(pageQuery.getPage(), pageQuery.getSize(), Sort.by(orders));
- } else {
- pageRequest = PageRequest.of(pageQuery.getPage(), pageQuery.getSize());
- }
- return pageRequest;
- }
- public <T> Specification<T> toSpecification(PageQuery pageQuery, Class<?> queryClass) {
- return (Specification<T>) (root, criteriaQuery, criteriaBuilder) -> {
- List<Predicate> and = new ArrayList<>();
- pageQuery.getQuery().forEach((property, value) -> {
- if (value == null) {
- return;
- }
- if (String.class.equals(value.getClass())) {
- if (StringUtils.isEmpty((String) value)) {
- return;
- }
- }
- Field field = getDeclaredField(queryClass, property);
- if (field == null) return;
- Class fieldType = field.getType();
- if (Enum.class.isAssignableFrom(fieldType)) {
- if (value instanceof Collection) {
- if (!((Collection) value).isEmpty()) {
- List list = new ArrayList();
- for (Object o : ((Collection) value)) {
- list.add(Enum.valueOf(fieldType, String.valueOf(o)));
- }
- and.add(root.get(property).in(list));
- }
- } else if (value instanceof String && StringUtils.isNotEmpty((String) value)) {
- if (((String) value).contains(",")) {
- String[] arr = ((String) value).split(",");
- List list = new ArrayList();
- for (String s : arr) {
- list.add(Enum.valueOf(fieldType, s));
- }
- and.add(root.get(property).in(list));
- } else {
- and.add(criteriaBuilder.and(criteriaBuilder
- .equal(root.get(property), Enum.valueOf(fieldType, String.valueOf(value)))));
- }
- }
- } else if (LocalDateTime.class == fieldType) {
- if (value instanceof List) {
- List list = (List) value;
- if (list.size() == 1) {
- LocalDateTime start = DateTimeUtils
- .toLocalDateTime((String) list.get(0), "yyyy-MM-dd HH:mm:ss");
- and.add(criteriaBuilder.greaterThanOrEqualTo(root.get(property), start));
- } else if (list.size() == 2) {
- LocalDateTime end = DateTimeUtils
- .toLocalDateTime((String) list.get(1), "yyyy-MM-dd HH:mm:ss");
- and.add(criteriaBuilder.lessThanOrEqualTo(root.get(property), end));
- }
- } else if (value instanceof String && Pattern
- .matches("^\\d{4}-\\d{2}-\\d{2} \\d{2}:\\d{2}:\\d{2},\\d{4}-\\d{2}-\\d{2} \\d{2}:\\d{2}:\\d{2}$", (String) value)) {
- String[] arr = ((String) value).split(",");
- LocalDateTime start = DateTimeUtils.toLocalDateTime(arr[0], "yyyy-MM-dd HH:mm:ss");
- and.add(criteriaBuilder.greaterThanOrEqualTo(root.get(property), start));
- LocalDateTime end = DateTimeUtils.toLocalDateTime(arr[1], "yyyy-MM-dd HH:mm:ss");
- and.add(criteriaBuilder.lessThanOrEqualTo(root.get(property), end));
- } else {
- and.add(criteriaBuilder.and(criteriaBuilder.equal(root.get(property), DateTimeUtils
- .toLocalDateTime((String) value, "yyyy-MM-dd HH:mm:ss"))));
- }
- } else if (LocalDate.class == fieldType) {
- if (value instanceof List) {
- List list = (List) value;
- if (list.size() == 1) {
- LocalDate start = DateTimeUtils
- .toLocalDate((String) list.get(0), "yyyy-MM-dd");
- and.add(criteriaBuilder.greaterThanOrEqualTo(root.get(property), start));
- } else if (list.size() == 2) {
- LocalDate end = DateTimeUtils
- .toLocalDate((String) list.get(1), "yyyy-MM-dd");
- and.add(criteriaBuilder.lessThanOrEqualTo(root.get(property), end));
- }
- } else if (value instanceof String && Pattern
- .matches("^\\d{4}-\\d{2}-\\d{2},\\d{4}-\\d{2}-\\d{2}$", (String) value)) {
- String[] arr = ((String) value).split(",");
- LocalDate start = DateTimeUtils.toLocalDate(arr[0], "yyyy-MM-dd");
- and.add(criteriaBuilder.greaterThanOrEqualTo(root.get(property), start));
- LocalDate end = DateTimeUtils.toLocalDate(arr[1], "yyyy-MM-dd");
- and.add(criteriaBuilder.lessThanOrEqualTo(root.get(property), end));
- } else {
- and.add(criteriaBuilder.and(criteriaBuilder.equal(root.get(property), DateTimeUtils
- .toLocalDateTime((String) value, "yyyy-MM-dd"))));
- }
- } else {
- and.add(criteriaBuilder.and(criteriaBuilder.equal(root.get(property), value)));
- }
- });
- if (StringUtils.isNotEmpty(pageQuery.getSearch())) {
- Field[] fields = queryClass.getDeclaredFields();
- List<Predicate> or = new ArrayList<>();
- try {
- if (StringUtils.isNumeric(pageQuery.getSearch())) {
- or.add(criteriaBuilder.equal(root.get("id"), Long.parseLong(pageQuery.getSearch())));
- }
- } catch (Exception ignored) {
- }
- for (Field field : fields) {
- Searchable annotation = field.getAnnotation(Searchable.class);
- if (annotation == null) {
- continue;
- }
- if (!annotation.value()) {
- continue;
- }
- or.add(criteriaBuilder.like(root.get(field.getName()), "%" + pageQuery.getSearch() + "%"));
- }
- and.add(criteriaBuilder.or(or.toArray(new Predicate[0])));
- }
- return criteriaBuilder.and(and.toArray(new Predicate[0]));
- };
- }
- private Field getDeclaredField(Class<?> clazz, String property) {
- String className = clazz.getName();
- while (clazz != null && clazz != Object.class) {
- try {
- return clazz.getDeclaredField(property);
- } catch (NoSuchFieldException ignored) {
- }
- clazz = clazz.getSuperclass();
- }
- log.error("no such field [{}] in class [{}]", property, className);
- return null;
- }
- }
|