You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

292 lines
9.8 KiB

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

package com.utils;
import java.util.Arrays;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import org.apache.commons.lang3.StringUtils;
import cn.hutool.core.bean.BeanUtil;
import com.baomidou.mybatisplus.mapper.Wrapper;
/**
* Mybatis-Plus工具类
*
* 核心职责提供MyBatis-Plus查询条件的便捷构建方法
*
* 功能特性:
* 1. 驼峰转下划线字段名转换
* 2. 对象属性到查询条件的自动转换
* 3. 多种查询条件构建(等值查询、模糊查询、范围查询、排序)
* 4. 支持前缀的字段名处理
*
* 技术依赖:
* - MyBatis-Plus: 查询条件构建
* - Hutool: Bean到Map的转换
* - Apache Commons Lang3: 字符串工具
*/
public class MPUtil {
// 下划线字符常量
public static final char UNDERLINE = '_';
/**
* MyBatis Plus allEQ 表达式转换(带前缀)
* 将Java Bean转换为数据库字段名的等值查询条件Map
*
* @param bean 实体对象
* @param pre 字段前缀(如表别名)
* @return 转换后的查询条件Map
*/
public static Map allEQMapPre(Object bean, String pre) {
Map<String, Object> map = BeanUtil.beanToMap(bean);
return camelToUnderlineMap(map, pre);
}
/**
* MyBatis Plus allEQ 表达式转换(无前缀)
* 将Java Bean转换为数据库字段名的等值查询条件Map
*
* @param bean 实体对象
* @return 转换后的查询条件Map
*/
public static Map allEQMap(Object bean) {
Map<String, Object> map = BeanUtil.beanToMap(bean);
return camelToUnderlineMap(map, "");
}
/**
* 构建带前缀的模糊查询条件
*
* @param wrapper MyBatis-Plus查询包装器
* @param bean 实体对象
* @param pre 字段前缀
* @return 构建后的查询包装器
*/
public static Wrapper allLikePre(Wrapper wrapper, Object bean, String pre) {
Map<String, Object> map = BeanUtil.beanToMap(bean);
Map result = camelToUnderlineMap(map, pre);
return genLike(wrapper, result);
}
/**
* 构建模糊查询条件
*
* @param wrapper MyBatis-Plus查询包装器
* @param bean 实体对象
* @return 构建后的查询包装器
*/
public static Wrapper allLike(Wrapper wrapper, Object bean) {
Map result = BeanUtil.beanToMap(bean, true, true);
return genLike(wrapper, result);
}
/**
* 生成模糊查询条件
* 为Map中的每个字段添加LIKE查询条件
*
* @param wrapper MyBatis-Plus查询包装器
* @param param 查询参数Map
* @return 构建后的查询包装器
*/
public static Wrapper genLike(Wrapper wrapper, Map param) {
Iterator<Map.Entry<String, Object>> it = param.entrySet().iterator();
int i = 0;
while (it.hasNext()) {
if (i > 0) wrapper.and(); // 从第二个条件开始添加AND连接
Map.Entry<String, Object> entry = it.next();
String key = entry.getKey();
String value = (String) entry.getValue();
wrapper.like(key, value); // 添加LIKE条件
i++;
}
return wrapper;
}
/**
* 构建模糊查询或等值查询条件
* 根据值是否包含%决定使用LIKE还是EQ
*
* @param wrapper MyBatis-Plus查询包装器
* @param bean 实体对象
* @return 构建后的查询包装器
*/
public static Wrapper likeOrEq(Wrapper wrapper, Object bean) {
Map result = BeanUtil.beanToMap(bean, true, true);
return genLikeOrEq(wrapper, result);
}
/**
* 生成模糊查询或等值查询条件
* 值包含%使用LIKE否则使用EQ
*
* @param wrapper MyBatis-Plus查询包装器
* @param param 查询参数Map
* @return 构建后的查询包装器
*/
public static Wrapper genLikeOrEq(Wrapper wrapper, Map param) {
Iterator<Map.Entry<String, Object>> it = param.entrySet().iterator();
int i = 0;
while (it.hasNext()) {
if (i > 0) wrapper.and();
Map.Entry<String, Object> entry = it.next();
String key = entry.getKey();
if (entry.getValue().toString().contains("%")) {
// 值包含%使用LIKE查询移除%符号)
wrapper.like(key, entry.getValue().toString().replace("%", ""));
} else {
// 值不包含%,使用等值查询
wrapper.eq(key, entry.getValue());
}
i++;
}
return wrapper;
}
/**
* 构建等值查询条件
*
* @param wrapper MyBatis-Plus查询包装器
* @param bean 实体对象
* @return 构建后的查询包装器
*/
public static Wrapper allEq(Wrapper wrapper, Object bean) {
Map result = BeanUtil.beanToMap(bean, true, true);
return genEq(wrapper, result);
}
/**
* 生成等值查询条件
* 为Map中的每个字段添加EQ查询条件
*
* @param wrapper MyBatis-Plus查询包装器
* @param param 查询参数Map
* @return 构建后的查询包装器
*/
public static Wrapper genEq(Wrapper wrapper, Map param) {
Iterator<Map.Entry<String, Object>> it = param.entrySet().iterator();
int i = 0;
while (it.hasNext()) {
if (i > 0) wrapper.and();
Map.Entry<String, Object> entry = it.next();
String key = entry.getKey();
wrapper.eq(key, entry.getValue()); // 添加等值条件
i++;
}
return wrapper;
}
/**
* 构建范围查询条件
* 处理以_start和_end结尾的字段生成BETWEEN条件
*
* @param wrapper MyBatis-Plus查询包装器
* @param params 查询参数Map
* @return 构建后的查询包装器
*/
public static Wrapper between(Wrapper wrapper, Map<String, Object> params) {
for (String key : params.keySet()) {
String columnName = "";
if (key.endsWith("_start")) {
// 处理开始范围条件
columnName = key.substring(0, key.indexOf("_start"));
if (StringUtils.isNotBlank(params.get(key).toString())) {
wrapper.ge(columnName, params.get(key)); // 大于等于
}
}
if (key.endsWith("_end")) {
// 处理结束范围条件
columnName = key.substring(0, key.indexOf("_end"));
if (StringUtils.isNotBlank(params.get(key).toString())) {
wrapper.le(columnName, params.get(key)); // 小于等于
}
}
}
return wrapper;
}
/**
* 构建排序条件
* 根据sort和order参数生成排序条件
*
* @param wrapper MyBatis-Plus查询包装器
* @param params 查询参数Map
* @return 构建后的查询包装器
*/
public static Wrapper sort(Wrapper wrapper, Map<String, Object> params) {
String order = "";
if (params.get("order") != null && StringUtils.isNotBlank(params.get("order").toString())) {
order = params.get("order").toString();
}
if (params.get("sort") != null && StringUtils.isNotBlank(params.get("sort").toString())) {
if (order.equalsIgnoreCase("desc")) {
wrapper.orderDesc(Arrays.asList(params.get("sort"))); // 降序
} else {
wrapper.orderAsc(Arrays.asList(params.get("sort"))); // 升序
}
}
return wrapper;
}
/**
* 驼峰格式字符串转换为下划线格式字符串
* 将Java字段名转换为数据库字段名
*
* @param param 驼峰格式字符串
* @return 下划线格式字符串
*/
public static String camelToUnderline(String param) {
if (param == null || "".equals(param.trim())) {
return "";
}
int len = param.length();
StringBuilder sb = new StringBuilder(len);
for (int i = 0; i < len; i++) {
char c = param.charAt(i);
if (Character.isUpperCase(c)) {
// 遇到大写字母,在前面添加下划线并转为小写
sb.append(UNDERLINE);
sb.append(Character.toLowerCase(c));
} else {
sb.append(c);
}
}
return sb.toString();
}
/**
* 测试方法
*/
public static void main(String[] ages) {
System.out.println(camelToUnderline("ABCddfANM")); // 输出: a_b_cddf_a_n_m
}
/**
* 将Map中的键从驼峰命名转换为下划线命名
*
* @param param 原始Map
* @param pre 字段前缀
* @return 转换后的Map
*/
public static Map camelToUnderlineMap(Map param, String pre) {
Map<String, Object> newMap = new HashMap<String, Object>();
Iterator<Map.Entry<String, Object>> it = param.entrySet().iterator();
while (it.hasNext()) {
Map.Entry<String, Object> entry = it.next();
String key = entry.getKey();
String newKey = camelToUnderline(key); // 转换字段名
// 处理前缀
if (pre.endsWith(".")) {
newMap.put(pre + newKey, entry.getValue());
} else if (StringUtils.isEmpty(pre)) {
newMap.put(newKey, entry.getValue());
} else {
newMap.put(pre + "." + newKey, entry.getValue());
}
}
return newMap;
}
}