您的位置:首页 > 数据库 > Mongodb

Spring Boot 使用AOP将日志存入MongoDB

2018-11-09 11:57 656 查看

虽然网上已经有很多使用AOP存入日志了,但我这个不一样。

1.使用最简单的代码直接从注解中获取值

2.支持SEL表达式获取参数中的值

注意事项:如果不用MongoDB就换成自己的方式,简单改一下罗。上代码了。

1.创建AOP拦截类 基本结构不用多说了

2.重点来了,将注解作为参数直接传入,即可直接获取注解中的值。无需通过反射获取。

[code]/**
* 需要切入的注解
*/
@Pointcut("@annotation(post2netAnno)")
public void initPost2netAnno(Post2MongodbAnno post2netAnno) {
}

@Before("initPost2netAnno(post2netAnno)")
public void doBefore(JoinPoint joinPoint, Post2MongodbAnno post2netAnno) {
ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
HttpServletRequest request = attributes.getRequest();

//url
log.info("url={}",request.getRequestURL());
//method
log.info("method={}",request.getMethod());
//ip
log.info("id={}",request.getRemoteAddr());
//class_method
log.info("class_method={}",joinPoint.getSignature().getDeclaringTypeName() + "," + joinPoint.getSignature().getName());
//args[]
ObjectMapper mapper = new ObjectMapper();
try {
String param = mapper.writeValueAsString(joinPoint.getArgs());
log.info("args={}",param);
} catch (JsonProcessingException e) {
e.printStackTrace();
}
}

@Around("initPost2netAnno(post2netAnno)")
public Object around(ProceedingJoinPoint pjp, Post2MongodbAnno post2netAnno) throws Throwable {
long startTime = System.currentTimeMillis();
Object  o = null;
Object[] args = pjp.getArgs();

final Object param = args[0];

StandardEvaluationContext standardEvaluationContext = new StandardEvaluationContext(pjp.getArgs());
standardEvaluationContext = setContextVariables(standardEvaluationContext, pjp);

try {
o = pjp.proceed();
sava2mogodb(standardEvaluationContext,post2netAnno,param,o,System.currentTimeMillis() - startTime);
log.info("☢☢☢:执行结果:{}",o);
return o;
}catch (Exception e){
//其他运行异常统一处理
log.error(e.toString()+":"+e.getMessage());
e.printStackTrace();
Result re =  Result.buildFail();
re.setMsg(e.getMessage());
sava2mogodb(standardEvaluationContext,post2netAnno,param,re,System.currentTimeMillis() - startTime);
return re;
}
}

3.通过SEL表达式获取 参数中的值

[code] private StandardEvaluationContext setContextVariables(StandardEvaluationContext standardEvaluationContext, ProceedingJoinPoint joinPoint) {

Object[] args = joinPoint.getArgs();

MethodSignature methodSignature = (MethodSignature) joinPoint.getSignature();

Method targetMethod = methodSignature.getMethod();

LocalVariableTableParameterNameDiscoverer parameterNameDiscoverer = new LocalVariableTableParameterNameDiscoverer();

String[] parametersName = parameterNameDiscoverer.getParameterNames(targetMethod);

if(args ==null|| args.length<=0) {

return standardEvaluationContext;

}
for(int i =0;i < args.length;i++) {

standardEvaluationContext.setVariable(parametersName[i],args[i]);

}
return standardEvaluationContext;
}

/**
* 通过key SEL表达式获取值
* @Author 张鹏
* @Date 2018/8/24 15:22
* @param key
* @param context
* @return
*/
private String getElValue(String key,StandardEvaluationContext context) {
if(StringUtils.isBlank(key)){
return "";
}
ExpressionParser parser =new SpelExpressionParser();

Expression exp = parser.parseExpression(key);

String value = exp.getValue(context,String.class);

return value;

}

4.大功告成,看看如何使用吧

框起来的就是SEL表达式罗。

注解中的内容怎么定义,我就不多说了。该有的关键代码已经全部加上去了

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: