|
@@ -1,6 +1,5 @@
|
|
package com.diagbot.aop;
|
|
package com.diagbot.aop;
|
|
|
|
|
|
-import com.alibaba.fastjson.JSONArray;
|
|
|
|
import com.alibaba.fastjson.JSONObject;
|
|
import com.alibaba.fastjson.JSONObject;
|
|
import com.auth0.jwt.JWT;
|
|
import com.auth0.jwt.JWT;
|
|
import com.auth0.jwt.exceptions.JWTDecodeException;
|
|
import com.auth0.jwt.exceptions.JWTDecodeException;
|
|
@@ -21,6 +20,7 @@ import com.diagbot.util.IpUtils;
|
|
import com.diagbot.util.ListUtil;
|
|
import com.diagbot.util.ListUtil;
|
|
import com.diagbot.util.StringUtil;
|
|
import com.diagbot.util.StringUtil;
|
|
import com.diagbot.util.SysUserUtils;
|
|
import com.diagbot.util.SysUserUtils;
|
|
|
|
+import com.diagbot.vo.QcCasesSaveListVO;
|
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
|
import eu.bitwalker.useragentutils.UserAgent;
|
|
import eu.bitwalker.useragentutils.UserAgent;
|
|
import org.apache.commons.collections4.MapUtils;
|
|
import org.apache.commons.collections4.MapUtils;
|
|
@@ -33,12 +33,17 @@ import org.aspectj.lang.annotation.Pointcut;
|
|
import org.springframework.beans.factory.annotation.Autowired;
|
|
import org.springframework.beans.factory.annotation.Autowired;
|
|
import org.springframework.security.web.util.matcher.AntPathRequestMatcher;
|
|
import org.springframework.security.web.util.matcher.AntPathRequestMatcher;
|
|
import org.springframework.stereotype.Component;
|
|
import org.springframework.stereotype.Component;
|
|
-import sun.plugin.cache.OldCacheEntry;
|
|
|
|
|
|
|
|
import javax.servlet.http.HttpServletRequest;
|
|
import javax.servlet.http.HttpServletRequest;
|
|
|
|
+import java.lang.reflect.Field;
|
|
|
|
+import java.util.ArrayList;
|
|
|
|
+import java.util.Arrays;
|
|
import java.util.Date;
|
|
import java.util.Date;
|
|
|
|
+import java.util.HashMap;
|
|
import java.util.List;
|
|
import java.util.List;
|
|
import java.util.Map;
|
|
import java.util.Map;
|
|
|
|
+import java.util.Set;
|
|
|
|
+import java.util.concurrent.atomic.AtomicReference;
|
|
|
|
|
|
/**
|
|
/**
|
|
* @Description:日志记录处理
|
|
* @Description:日志记录处理
|
|
@@ -58,10 +63,10 @@ public class LogAspect {
|
|
|
|
|
|
// 操作配置织入点
|
|
// 操作配置织入点
|
|
@Pointcut("execution(public * com.diagbot.web.*.*(..))" +
|
|
@Pointcut("execution(public * com.diagbot.web.*.*(..))" +
|
|
- "&& !execution(public * com.diagbot.web.SysUserController.getJwt(..))"+
|
|
|
|
- "&& !execution(public * com.diagbot.web.SysUserController.getCaptcha(..))"+
|
|
|
|
- "&& !execution(public * com.diagbot.web.SysUserController.getJwtNoPass(..))"+
|
|
|
|
- "&& !execution(public * com.diagbot.web.SysUserController.getHospitalMark(..))"+
|
|
|
|
|
|
+ "&& !execution(public * com.diagbot.web.SysUserController.getJwt(..))" +
|
|
|
|
+ "&& !execution(public * com.diagbot.web.SysUserController.getCaptcha(..))" +
|
|
|
|
+ "&& !execution(public * com.diagbot.web.SysUserController.getJwtNoPass(..))" +
|
|
|
|
+ "&& !execution(public * com.diagbot.web.SysUserController.getHospitalMark(..))" +
|
|
"&& !execution(public * com.diagbot.web.SysUserController.midifyPassword(..))"
|
|
"&& !execution(public * com.diagbot.web.SysUserController.midifyPassword(..))"
|
|
)
|
|
)
|
|
public void operPointCut() {
|
|
public void operPointCut() {
|
|
@@ -97,93 +102,217 @@ public class LogAspect {
|
|
try {
|
|
try {
|
|
//1.去sys_hospital_set表中拿所有需要进行操作日志记录的url
|
|
//1.去sys_hospital_set表中拿所有需要进行操作日志记录的url
|
|
List<SysHospitalSet> hospitalSets = sysHospitalSetFacade
|
|
List<SysHospitalSet> hospitalSets = sysHospitalSetFacade
|
|
- .getHospitalSetByRemark(Long.parseLong(SysUserUtils.getCurrentHospitalID()),"operationLog");
|
|
|
|
- if(ListUtil.isNotEmpty(hospitalSets)){
|
|
|
|
- havingOperation(hospitalSets,HttpUtils.getHttpServletRequest(),joinPoint);
|
|
|
|
|
|
+ .getHospitalSetByRemark(Long.parseLong(SysUserUtils.getCurrentHospitalID()), "operationLog");
|
|
|
|
+ if (ListUtil.isNotEmpty(hospitalSets)) {
|
|
|
|
+ havingOperation(hospitalSets, HttpUtils.getHttpServletRequest(), joinPoint);
|
|
}
|
|
}
|
|
- }catch (Exception e){
|
|
|
|
|
|
+ } catch (Exception e) {
|
|
e.printStackTrace();
|
|
e.printStackTrace();
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
- private void havingOperation(List<SysHospitalSet> hospitalSets, HttpServletRequest httpServletRequest,JoinPoint joinPoint) {
|
|
|
|
|
|
+ private void havingOperation(List<SysHospitalSet> hospitalSets, HttpServletRequest httpServletRequest, JoinPoint joinPoint) {
|
|
|
|
+ StringBuffer operationRecordBuffer = new StringBuffer();
|
|
|
|
+ //结果拼接容器
|
|
|
|
+ Map<String, Object> outMap = new HashMap<>();
|
|
//1.判断该请求是否需要操作日志记录
|
|
//1.判断该请求是否需要操作日志记录
|
|
- hospitalSets.stream().forEach(hospitalSet->{
|
|
|
|
- if(matchers(hospitalSet.getCode(),httpServletRequest)){
|
|
|
|
- String params = getControllerMethodDescription(joinPoint);
|
|
|
|
|
|
+ hospitalSets.stream().forEach(hospitalSet -> {
|
|
|
|
+ if (matchers(hospitalSet.getCode(), httpServletRequest)) {
|
|
|
|
+ operationUrlHandler(outMap, HttpUtils.getHttpServletRequest().getRequestURI(), joinPoint);
|
|
|
|
+ String operationRecord = makeOperationRecord(hospitalSet.getValue(), outMap);
|
|
|
|
+ if (!operationRecord.contains("#")) {
|
|
|
|
+ operationRecordBuffer.append(operationRecord).append(";");
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ // try {
|
|
|
|
+ // //由于两个对象大多结构不一样(例如:obj list),对比先不统一处理,放到case中每个方法单独处理
|
|
|
|
+ // Object old = getOldOperation(HttpUtils.getHttpServletRequest().getRequestURI(), params);
|
|
|
|
+ // Object[] args = joinPoint.getArgs();
|
|
|
|
+ // if (args != null && args.length > 0){
|
|
|
|
+ // for(int i = 0;i<args.length;i++){
|
|
|
|
+ // //对比
|
|
|
|
+ // comparePara(old, args[i]);
|
|
|
|
+ // }
|
|
|
|
+ //
|
|
|
|
+ // }
|
|
|
|
+ // } catch (Exception e) {
|
|
|
|
+ // e.printStackTrace();
|
|
|
|
+ // }
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ });
|
|
|
|
+ //保存操作记录
|
|
|
|
+ saveOperationLog(joinPoint, operationRecordBuffer.toString());
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ private void saveOperationLog(JoinPoint joinPoint, String operationRecord) {
|
|
|
|
+ try {
|
|
|
|
+ if (StringUtil.isNotBlank(operationRecord)) {
|
|
|
|
+ SysOperationLogDTO operationLog = new SysOperationLogDTO();
|
|
|
|
+ Date date = new Date();
|
|
|
|
+ operationLog.setOperationDate(date);
|
|
|
|
+ operationLog.setGmtCreate(date);
|
|
|
|
+ operationLog.setOperationId(SysUserUtils.getCurrentPrincipleID());
|
|
|
|
+ operationLog.setOperationName(SysUserUtils.getCurrentPrinciple());
|
|
|
|
+ String ip = HttpUtils.getIpAddress();
|
|
|
|
+ if (IpUtils.isIPv4LiteralAddress(ip)) {
|
|
|
|
+ operationLog.setOperationIp(ip);
|
|
|
|
+ } else {
|
|
|
|
+ operationLog.setRemark("[非ipv4地址]:" + ip);
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ // 设置方法名称
|
|
|
|
+ String className = joinPoint.getTarget().getClass().getName();
|
|
|
|
+ String methodName = joinPoint.getSignature().getName();
|
|
|
|
+ operationLog.setOperationMethod(className + "." + methodName + "()");
|
|
|
|
+ // 设置请求方式
|
|
|
|
+ operationLog.setOperationWay(HttpUtils.getHttpServletRequest().getMethod());
|
|
|
|
+ operationLog.setOperationUrl(HttpUtils.getHttpServletRequest().getRequestURI());
|
|
|
|
+ // 处理设置注解上的参数
|
|
try {
|
|
try {
|
|
- String old = getOldOperation(HttpUtils.getHttpServletRequest().getRequestURI(),params);
|
|
|
|
- //对比
|
|
|
|
- comparePara(old,params);
|
|
|
|
- }catch (Exception e){
|
|
|
|
|
|
+ String params = getControllerMethodDescription(joinPoint);
|
|
|
|
+ if (StringUtils.isNotBlank(params)) {
|
|
|
|
+ operationLog.setOperationParam(params);
|
|
|
|
+ }
|
|
|
|
+ } catch (Exception e) {
|
|
e.printStackTrace();
|
|
e.printStackTrace();
|
|
}
|
|
}
|
|
|
|
+ operationLog.setIsPlacefile(SysUserUtils.getIsPlacefile() == null ? "0" : SysUserUtils.getIsPlacefile());
|
|
|
|
+ operationLog.setOperationRecord(operationRecord.substring(0, operationRecord.length() - 1));
|
|
|
|
+ operationLogFacade.getBaseMapper().addOperationRecord(operationLog);
|
|
}
|
|
}
|
|
- });
|
|
|
|
|
|
+ } catch (Exception e) {
|
|
|
|
+ e.printStackTrace();
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ private String makeOperationRecord(String value, Map<String, Object> outMap) {
|
|
|
|
+ if (StringUtil.isBlank(value) || outMap.keySet().size() == 0) {
|
|
|
|
+ return null;
|
|
|
|
+ }
|
|
|
|
+ for (String key : outMap.keySet()) {
|
|
|
|
+ if (value.contains(key)) {
|
|
|
|
+ value = value.replaceAll(key, outMap.get(key) + "");
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+ return value;
|
|
}
|
|
}
|
|
|
|
|
|
- private void comparePara(String old, String params) {
|
|
|
|
- //对比新旧数据变化
|
|
|
|
|
|
+ private void comparePara(Object old, Object params, Map<String, Object> outMap) {
|
|
|
|
+ try {
|
|
|
|
+ //对比新旧数据变化
|
|
|
|
+ compareTwoClass(old, params, outMap);
|
|
|
|
+ //拼接操作结果
|
|
|
|
+ } catch (Exception e) {
|
|
|
|
+ e.printStackTrace();
|
|
|
|
+ }
|
|
|
|
|
|
- //拼接操作结果
|
|
|
|
}
|
|
}
|
|
|
|
|
|
- private String getOldOperation(String requestURI,String params) {
|
|
|
|
- String out = "";
|
|
|
|
- switch (requestURI){
|
|
|
|
- case "/qc/cases/saveQcCases"://修改模块分值
|
|
|
|
- if(StringUtil.isNotEmpty(params)){
|
|
|
|
- //通过id获取模块名称以及目前分值
|
|
|
|
- JSONArray paramsArr = JSONArray.parseArray(params);
|
|
|
|
- QcCasesDTO old = operationLogFacade.getQcCasesById(paramsArr.getJSONObject(0).getString("id"));
|
|
|
|
- out = old.toString();
|
|
|
|
|
|
+
|
|
|
|
+ public static void compareTwoClass(Object class1, Object class2, Map<String, Object> outMap) {
|
|
|
|
+ //获取对象的class
|
|
|
|
+ Class<?> clazz1 = class1.getClass();
|
|
|
|
+ Class<?> clazz2 = class2.getClass();
|
|
|
|
+ //获取对象的属性列表
|
|
|
|
+ Field[] field1 = clazz1.getDeclaredFields();
|
|
|
|
+ Field[] field2 = clazz2.getDeclaredFields();
|
|
|
|
+ List<String> fieldList1 = new ArrayList<>();
|
|
|
|
+ for (Field field : field1) {
|
|
|
|
+ fieldList1.add(field.getName());
|
|
|
|
+ }
|
|
|
|
+ for (Field field : field2) {
|
|
|
|
+ fieldList1.remove(field.getName());
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ //遍历属性列表field1
|
|
|
|
+ for (int i = 0; i < field1.length; i++) {
|
|
|
|
+ field1[i].setAccessible(true);
|
|
|
|
+ //遍历属性列表field2
|
|
|
|
+ for (int j = 0; j < field2.length; j++) {
|
|
|
|
+ //如果field1[i]属性名与field2[j]属性名内容相同
|
|
|
|
+ if (field1[i].getName().equals(field2[j].getName())) {
|
|
|
|
+ field2[j].setAccessible(true);
|
|
|
|
+ try {
|
|
|
|
+ //如果field1[i]属性值与field2[j]属性值内容不相同
|
|
|
|
+ if (!compareTwo(field1[i].get(class1), field2[j].get(class2))) {
|
|
|
|
+ outMap.put("#" + field1[i].getName() + "_old", field1[i].get(class1));
|
|
|
|
+ outMap.put("#" + field1[i].getName() + "_new", field2[j].get(class2));
|
|
|
|
+ }
|
|
|
|
+ } catch (Exception e) {
|
|
|
|
+ e.printStackTrace();
|
|
|
|
+ }
|
|
|
|
+ break;
|
|
}
|
|
}
|
|
- break;
|
|
|
|
|
|
+ }
|
|
|
|
+ //把old中有的属性new中没有的加入map
|
|
|
|
+ if (fieldList1.contains(field1[i].getName())) {
|
|
|
|
+ try {
|
|
|
|
+ outMap.put("#" + field1[i].getName(), field1[i].get(class1));
|
|
|
|
+ } catch (IllegalAccessException e) {
|
|
|
|
+ e.printStackTrace();
|
|
|
|
+ }
|
|
|
|
+ }
|
|
}
|
|
}
|
|
- return out;
|
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
+ //对比两个数据是否内容相同
|
|
|
|
+ public static boolean compareTwo(Object object1, Object object2) {
|
|
|
|
|
|
- /**
|
|
|
|
- * 返回信息相同日志代码复用
|
|
|
|
- *
|
|
|
|
- * @param joinPoint
|
|
|
|
- * @Return com.diagbot.dto.SysOperationLogDTO
|
|
|
|
- */
|
|
|
|
- public SysOperationLogDTO multiplexing(JoinPoint joinPoint) {
|
|
|
|
-
|
|
|
|
- SysOperationLogDTO operationLog = new SysOperationLogDTO();
|
|
|
|
- Date date = new Date();
|
|
|
|
- operationLog.setOperationDate(date);
|
|
|
|
- operationLog.setGmtCreate(date);
|
|
|
|
- operationLog.setOperationId(SysUserUtils.getCurrentPrincipleID() == null ? 0l : Long.parseLong(SysUserUtils.getCurrentPrincipleID()));
|
|
|
|
- operationLog.setOperationName(SysUserUtils.getCurrentPrinciple());
|
|
|
|
- String ip = HttpUtils.getIpAddress();
|
|
|
|
- if (IpUtils.isIPv4LiteralAddress(ip)) {
|
|
|
|
- operationLog.setOperationIp(ip);
|
|
|
|
- } else {
|
|
|
|
- operationLog.setRemark("[非ipv4地址]:" + ip);
|
|
|
|
|
|
+ if (object1 == null && object2 == null) {
|
|
|
|
+ return true;
|
|
}
|
|
}
|
|
|
|
+ if (object1 == null && object2 != null) {
|
|
|
|
+ return false;
|
|
|
|
+ }
|
|
|
|
+ if (object1.equals(object2)) {
|
|
|
|
+ return true;
|
|
|
|
+ }
|
|
|
|
+ return false;
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ private Object getOldOperation(String requestURI, String params) {
|
|
|
|
+ switch (requestURI) {
|
|
|
|
+ case "/qc/cases/saveQcCases"://修改模块分值
|
|
|
|
+ if (StringUtil.isNotEmpty(params)) {
|
|
|
|
+ //通过id获取模块名称以及目前分值
|
|
|
|
+ JSONObject paramJSON = JSONObject.parseObject(params);
|
|
|
|
+ QcCasesDTO old = operationLogFacade.getQcCasesById(paramJSON.getJSONArray("qcCasesSaveVOList")
|
|
|
|
+ .getJSONObject(0).getString("id"));
|
|
|
|
+ return old;
|
|
|
|
+ }
|
|
|
|
+ break;
|
|
|
|
+ }
|
|
|
|
+ return null;
|
|
|
|
+ }
|
|
|
|
|
|
- // 设置方法名称
|
|
|
|
- String className = joinPoint.getTarget().getClass().getName();
|
|
|
|
- String methodName = joinPoint.getSignature().getName();
|
|
|
|
- operationLog.setOperationMethod(className + "." + methodName + "()");
|
|
|
|
- // 设置请求方式
|
|
|
|
- operationLog.setOperationWay(HttpUtils.getHttpServletRequest().getMethod());
|
|
|
|
- operationLog.setOperationUrl(HttpUtils.getHttpServletRequest().getRequestURI());
|
|
|
|
- // 处理设置注解上的参数
|
|
|
|
|
|
+ private void operationUrlHandler(Map<String, Object> outMap, String requestURI, JoinPoint joinPoint) {
|
|
try {
|
|
try {
|
|
- String params = getControllerMethodDescription(joinPoint);
|
|
|
|
- if (StringUtils.isNotBlank(params)) {
|
|
|
|
- operationLog.setOperationParam(params);
|
|
|
|
|
|
+ switch (requestURI) {
|
|
|
|
+ case "/qc/cases/saveQcCases"://修改模块分值
|
|
|
|
+ Object[] args = joinPoint.getArgs();
|
|
|
|
+ if (null != args && args.length >= 0) {
|
|
|
|
+ //通过id获取模块名称以及目前分值
|
|
|
|
+ if (args[0] instanceof QcCasesSaveListVO) {
|
|
|
|
+ QcCasesSaveListVO qcCasesSaveListVO = (QcCasesSaveListVO) args[0];
|
|
|
|
+ QcCasesDTO old = operationLogFacade.getQcCasesById(qcCasesSaveListVO.getQcCasesSaveVOList().get(0).getId() + "");
|
|
|
|
+ compareTwoClass(old, qcCasesSaveListVO.getQcCasesSaveVOList().get(0), outMap);
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+ break;
|
|
|
|
+ case "/sys/user/disable":
|
|
|
|
+ compareTwoClass("旧结果对象", "新的入参对象", outMap);
|
|
|
|
+ break;
|
|
|
|
+
|
|
|
|
+ default:
|
|
|
|
+ break;
|
|
}
|
|
}
|
|
} catch (Exception e) {
|
|
} catch (Exception e) {
|
|
e.printStackTrace();
|
|
e.printStackTrace();
|
|
}
|
|
}
|
|
- return operationLog;
|
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
+
|
|
/**
|
|
/**
|
|
* @Description:获取请求的参数
|
|
* @Description:获取请求的参数
|
|
* @Param: [joinPoint, logInformation]
|
|
* @Param: [joinPoint, logInformation]
|
|
@@ -273,7 +402,7 @@ public class LogAspect {
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
- private boolean matchers(String url,HttpServletRequest request) {
|
|
|
|
|
|
+ private boolean matchers(String url, HttpServletRequest request) {
|
|
AntPathRequestMatcher matcher = new AntPathRequestMatcher(url);
|
|
AntPathRequestMatcher matcher = new AntPathRequestMatcher(url);
|
|
if (matcher.matches(request)) {
|
|
if (matcher.matches(request)) {
|
|
return true;
|
|
return true;
|