|
@@ -0,0 +1,192 @@
|
|
|
+package com.hys.app.framework.database.mybatisplus.base;
|
|
|
+
|
|
|
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
|
|
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
|
|
|
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
|
|
|
+import com.fasterxml.jackson.databind.ObjectMapper;
|
|
|
+import com.fasterxml.jackson.databind.SerializationFeature;
|
|
|
+import lombok.extern.slf4j.Slf4j;
|
|
|
+import org.apache.ibatis.executor.Executor;
|
|
|
+import org.apache.ibatis.mapping.MappedStatement;
|
|
|
+import org.apache.ibatis.mapping.SqlCommandType;
|
|
|
+import org.apache.ibatis.plugin.*;
|
|
|
+import org.springframework.beans.factory.annotation.Autowired;
|
|
|
+import org.springframework.context.ApplicationContext;
|
|
|
+import org.springframework.stereotype.Component;
|
|
|
+
|
|
|
+import java.io.Serializable;
|
|
|
+import java.lang.reflect.Field;
|
|
|
+import java.util.Collection;
|
|
|
+import java.util.Map;
|
|
|
+import java.util.Properties;
|
|
|
+
|
|
|
+@Slf4j
|
|
|
+@Component
|
|
|
+@Intercepts({
|
|
|
+ @Signature(type = Executor.class, method = "update", args = {MappedStatement.class, Object.class})
|
|
|
+})
|
|
|
+public class DeleteOperationInterceptor implements Interceptor {
|
|
|
+
|
|
|
+ @Autowired
|
|
|
+ private ApplicationContext applicationContext;
|
|
|
+
|
|
|
+ private final ObjectMapper objectMapper;
|
|
|
+
|
|
|
+ public DeleteOperationInterceptor() {
|
|
|
+ this.objectMapper = new ObjectMapper();
|
|
|
+ this.objectMapper.configure(SerializationFeature.FAIL_ON_EMPTY_BEANS, false);
|
|
|
+ }
|
|
|
+
|
|
|
+ @Override
|
|
|
+ @SuppressWarnings({"unchecked", "rawtypes"})
|
|
|
+ public Object intercept(Invocation invocation) throws Throwable {
|
|
|
+ MappedStatement ms = (MappedStatement) invocation.getArgs()[0];
|
|
|
+ Object parameter = invocation.getArgs()[1];
|
|
|
+
|
|
|
+ // 只处理删除操作
|
|
|
+ if (ms.getSqlCommandType() == SqlCommandType.DELETE) {
|
|
|
+ String methodId = ms.getId();
|
|
|
+ // 获取表名
|
|
|
+ String tableName = extractTableName(ms);
|
|
|
+
|
|
|
+ try {
|
|
|
+ String mapperClassName = methodId.substring(0, methodId.lastIndexOf("."));
|
|
|
+ Class<?> mapperClass = Class.forName(mapperClassName);
|
|
|
+ BaseMapper mapper = (BaseMapper) applicationContext.getBean(mapperClass);
|
|
|
+
|
|
|
+ // 获取要删除的数据和条件
|
|
|
+ Object deleteData = null;
|
|
|
+ String deleteCondition = "";
|
|
|
+
|
|
|
+ if (parameter instanceof Map) {
|
|
|
+ Map<String, Object> paramMap = (Map<String, Object>) parameter;
|
|
|
+ if (paramMap.containsKey("et")) {
|
|
|
+ Object entity = paramMap.get("et");
|
|
|
+ deleteData = mapper.selectById(getEntityId(entity));
|
|
|
+ deleteCondition = "根据ID: " + getEntityId(entity);
|
|
|
+ } else if (paramMap.containsKey("ew")) {
|
|
|
+ Object wrapper = paramMap.get("ew");
|
|
|
+ deleteCondition = extractDeleteCondition(wrapper);
|
|
|
+ if (wrapper instanceof QueryWrapper) {
|
|
|
+ deleteData = mapper.selectList((QueryWrapper) wrapper);
|
|
|
+ } else if (wrapper instanceof LambdaQueryWrapper) {
|
|
|
+ deleteData = mapper.selectList((LambdaQueryWrapper) wrapper);
|
|
|
+ }
|
|
|
+ } else if (paramMap.containsKey("array")) {
|
|
|
+ Collection ids = (Collection) paramMap.get("array");
|
|
|
+ deleteData = mapper.selectBatchIds(ids);
|
|
|
+ deleteCondition = "批量删除ID: " + ids;
|
|
|
+ }
|
|
|
+ } else if (parameter != null) {
|
|
|
+ if (parameter instanceof Serializable) {
|
|
|
+ deleteData = mapper.selectById((Serializable) parameter);
|
|
|
+ deleteCondition = "根据ID: " + parameter;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ // 记录删除操作
|
|
|
+ String caller = getCallerInfo();
|
|
|
+ log.info("\n删除操作 - " +
|
|
|
+ "\n调用者: {}" +
|
|
|
+ "\n方法: {}" +
|
|
|
+ "\n表名: {}" +
|
|
|
+ "\n删除条件: {}" +
|
|
|
+ "\n删除数据: {}",
|
|
|
+ caller,
|
|
|
+ methodId,
|
|
|
+ tableName,
|
|
|
+ deleteCondition,
|
|
|
+ toJsonString(deleteData));
|
|
|
+
|
|
|
+ } catch (Exception e) {
|
|
|
+ log.error("获取删除数据失败", e);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ return invocation.proceed();
|
|
|
+ }
|
|
|
+
|
|
|
+ private String extractTableName(MappedStatement ms) {
|
|
|
+ try {
|
|
|
+ // 从SQL语句中提取表名
|
|
|
+ String sql = ms.getBoundSql(null).getSql();
|
|
|
+ // DELETE FROM table_name ...
|
|
|
+ String[] parts = sql.split("\\s+");
|
|
|
+ if (parts.length >= 3) {
|
|
|
+ return parts[2].trim();
|
|
|
+ }
|
|
|
+ } catch (Exception e) {
|
|
|
+ log.warn("无法从SQL提取表名", e);
|
|
|
+ }
|
|
|
+ return "";
|
|
|
+ }
|
|
|
+
|
|
|
+ private String extractDeleteCondition(Object wrapper) {
|
|
|
+ try {
|
|
|
+ if (wrapper instanceof QueryWrapper) {
|
|
|
+ QueryWrapper qw = (QueryWrapper) wrapper;
|
|
|
+ Map<String, Object> paramNameValuePairs = qw.getParamNameValuePairs();
|
|
|
+ String targetSql = qw.getTargetSql();
|
|
|
+ // 替换参数占位符
|
|
|
+ for (Map.Entry<String, Object> entry : paramNameValuePairs.entrySet()) {
|
|
|
+ targetSql = targetSql.replaceFirst("\\?", String.valueOf(entry.getValue()));
|
|
|
+ }
|
|
|
+ return targetSql;
|
|
|
+ } else if (wrapper instanceof LambdaQueryWrapper) {
|
|
|
+ LambdaQueryWrapper lqw = (LambdaQueryWrapper) wrapper;
|
|
|
+ Map<String, Object> paramNameValuePairs = lqw.getParamNameValuePairs();
|
|
|
+ String targetSql = lqw.getTargetSql();
|
|
|
+ // 替换参数占位符
|
|
|
+ for (Map.Entry<String, Object> entry : paramNameValuePairs.entrySet()) {
|
|
|
+ targetSql = targetSql.replaceFirst("\\?", String.valueOf(entry.getValue()));
|
|
|
+ }
|
|
|
+ return targetSql;
|
|
|
+ }
|
|
|
+ } catch (Exception e) {
|
|
|
+ log.warn("提取删除条件失败", e);
|
|
|
+ }
|
|
|
+ return wrapper.toString();
|
|
|
+ }
|
|
|
+
|
|
|
+ private String getCallerInfo() {
|
|
|
+ StackTraceElement[] stackTrace = Thread.currentThread().getStackTrace();
|
|
|
+ for (StackTraceElement element : stackTrace) {
|
|
|
+ String className = element.getClassName();
|
|
|
+ if (className.contains("service") && !className.contains("$")) {
|
|
|
+ return className + "." + element.getMethodName() + ":" + element.getLineNumber();
|
|
|
+ }
|
|
|
+ }
|
|
|
+ return "Unknown";
|
|
|
+ }
|
|
|
+
|
|
|
+ private Serializable getEntityId(Object entity) {
|
|
|
+ try {
|
|
|
+ // 尝试获取id字段
|
|
|
+ Field idField = entity.getClass().getDeclaredField("id");
|
|
|
+ idField.setAccessible(true);
|
|
|
+ return (Serializable) idField.get(entity);
|
|
|
+ } catch (Exception e) {
|
|
|
+ log.warn("获取实体ID失败", e);
|
|
|
+ return null;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ private String toJsonString(Object obj) {
|
|
|
+ try {
|
|
|
+ return objectMapper.writeValueAsString(obj);
|
|
|
+ } catch (Exception e) {
|
|
|
+ log.warn("JSON序列化失败", e);
|
|
|
+ return String.valueOf(obj);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ @Override
|
|
|
+ public Object plugin(Object target) {
|
|
|
+ return Plugin.wrap(target, this);
|
|
|
+ }
|
|
|
+
|
|
|
+ @Override
|
|
|
+ public void setProperties(Properties properties) {
|
|
|
+ // 可以添加配置项
|
|
|
+ }
|
|
|
+}
|