Skip to content
CustomPlugin.java 5.21 KiB
Newer Older
zhangshuhao's avatar
zhangshuhao committed
package com.Config;

import org.apache.ibatis.binding.MapperMethod;
import org.apache.ibatis.cache.CacheKey;
import org.apache.ibatis.executor.Executor;
import org.apache.ibatis.mapping.BoundSql;
import org.apache.ibatis.mapping.MappedStatement;
import org.apache.ibatis.mapping.ParameterMapping;
import org.apache.ibatis.plugin.Interceptor;
import org.apache.ibatis.plugin.Intercepts;
import org.apache.ibatis.plugin.Invocation;
import org.apache.ibatis.plugin.Plugin;
import org.apache.ibatis.plugin.Signature;
import org.apache.ibatis.session.ResultHandler;
import org.apache.ibatis.session.RowBounds;

import java.util.HashMap;
import java.util.List;
import java.util.Properties;

@Intercepts(
  {
    @Signature(type = Executor.class, method = "query", args = {MappedStatement.class, Object.class, RowBounds.class, ResultHandler.class, CacheKey.class, BoundSql.class}),
    @Signature(type = Executor.class, method = "query", args = {MappedStatement.class, Object.class, RowBounds.class, ResultHandler.class}),
    @Signature(type = Executor.class, method = "update", args = {MappedStatement.class, Object.class})
  }
)
public class CustomPlugin implements Interceptor {

  @Override
  public Object intercept(Invocation invocation) throws Throwable {
    Object[] args = invocation.getArgs();
    MappedStatement ms = (MappedStatement) args[0];
    Object parameter = args[1];
    Executor executor = (Executor) invocation.getTarget();
    CacheKey cacheKey = null;
    BoundSql boundSql = null;
    Class<?> type = ms.getParameterMap().getType();

    if (args.length >= 4) {
      boundSql = ms.getBoundSql(parameter);
      ResultHandler resultHandler = (ResultHandler) args[3];
      RowBounds rowBounds = (RowBounds) args[2];
      cacheKey = executor.createCacheKey(ms, parameter, rowBounds, boundSql);
      if (args.length == 6) {
        cacheKey = (CacheKey) args[4];
        boundSql = (BoundSql) args[5];
      }
      String sql = getSql(boundSql, type);
      //log.debug("runing query(dql) sql:{}", sql);
      return executor.query(ms, parameter, rowBounds, resultHandler, cacheKey, boundSql);
    } else if (args.length == 2) {
      // update
      boundSql = ms.getBoundSql(parameter);
      String sql = getSql(boundSql, type);
      //log.debug("runing update(dml) sql:{}", sql);
      return executor.update(ms, parameter);
    } else {
      throw new RuntimeException("无效拦截");
    }
  }

  private String getSql(BoundSql boundSql, Class<?> type) {
    String sql = boundSql.getSql();
    final String[] temp = {sql};
    if (sql.contains("?") && boundSql.getParameterMappings().size() > 0 && boundSql.getParameterObject() != null) {
      List<ParameterMapping> parameterMappings = boundSql.getParameterMappings();
      Object parameterObject = boundSql.getParameterObject();
      //多参数
      if (parameterObject instanceof HashMap) {
        MapperMethod.ParamMap parameterObject1 = (MapperMethod.ParamMap) parameterObject;
        parameterMappings.forEach(parameters -> {
          String property = parameters.getProperty();
          // todo 拦截过滤,大小过滤
          String strs = String.valueOf(parameterObject1.get(property));
          if (strs != null) {
            temp[0] = temp[0].replaceFirst("\\?", "'" + strs + "'");
          }
        });
      } else if (parameterObject instanceof String) {
        // 单参数
        parameterMappings.forEach(parameters -> {
          // todo 拦截过滤,大小过滤
          String strs = String.valueOf(parameterObject);
          temp[0] = temp[0].replaceFirst("\\?", "'" + strs + "'");

        });
      } else if (parameterObject.getClass().isAssignableFrom(type)) {
        // 对象类型
        String ss = parameterObject.toString();
        String substring = ss;
        String[] strings = new String[1];
        strings[0] = ss;
        substring = substring.replaceFirst("\\(", "");
        substring = substring.replaceFirst("\\)", "");
        if (substring.contains("(") || substring.contains(")")) {
          // 不管, 显示全部j对象数据
        } else {
          substring = strings[0];
          substring = substring.replaceAll(" ", "");
          HashMap<String, String> map = new HashMap<>();
          int i = substring.indexOf("(");
          int i1 = substring.lastIndexOf(")");
          if (i != -1 && i1 != -1) {
            substring = substring.substring(i + 1, i1);
          }
          // 若不存在复合类型的精准提供
          String[] split = substring.split(",");
          if (split.length > 0) {
            for (String s : split) {
              int i2 = s.indexOf("=");
              String key = s.substring(0, i2);
              String value = s.substring(i2 + 1);
              map.put(key, value);
            }
          }
          parameterMappings.forEach(parameters -> {
            String property = parameters.getProperty();
            String strs = String.valueOf(map.get(property));
            temp[0] = temp[0].replaceFirst("\\?", "'" + strs + "'");

          });

        }

      }

    }
    //TODO 自己要进行的各种处理
    return temp[0];
  }

  @Override
  public Object plugin(Object target) {
    return Plugin.wrap(target, this);
  }

  @Override
  public void setProperties(Properties properties) {
    //
  }

}