起因: 项目重构, 期间要拦截请求加日志, 后期日志处理得到数据. 但是一部分内容是MQ推过来的, 发现推过来的部分拦截不到, 如: send发送内容, this.send(xxx)直接发送, send的日志无法拦截.
解决方案: 使用spring填充的类进行调用, MaapSendController 类内增加MaapSendController 的@Autowired实例, 使用该实例可以被AOP拦截到.
/**
* controller实例
*/
@Autowired
private MaapSendController maapSendController;
/**
* 监听器实例
*/
@Autowired
private MQMessageListener listenerConcurrently;
/**
* 生产者实例
*/
@Autowired
@Qualifier("DefaultMQProducer")
private DefaultMQProducer DefaultMQProducer;
/**
* 初始化mq消费
*/
@PostConstruct
public void registryListener(){
// DisableSSLCertificateCheckUtil.disableChecks();
listenerConcurrently.addListener((msgs, context) -> {
for(MessageExt msg : msgs) {
try {
String topic = msg.getTopic();
log.info("topic = " + topic);
byte[] body = msg.getBody();
log.info("body: " + new String(body));
String keys = msg.getKeys();
log.info("keys = " + keys);
String tags = msg.getTags();
log.info("tags = " + tags);
String bodyJson = new String(body);
Message5gSend bodyObj = JSONUtil.toBean(bodyJson, Message5gSend.class, false);
maapSendController.send(bodyObj);
}catch (Exception e){
log.error("消息消费失败: {}", e.getMessage());
}
}
return ConsumeConcurrentlyStatus.CONSUME_SUCCESS;
});
}
但是这样拦截的时候发现send的参数在拦截的时候getArgs()是Null, 但是我断点的时候却发现point内的methodInvocation内是有参数内容的, 看MethodInvocationProceedingJoinPoint的源码内的getArgs也是能够从这里存在的位置获取参数的. 于是我尝试把point转换为MethodInvocationProceedingJoinPoint后再次getArgs(), 就特么出来了....看来类型下转后getArgs的实现跟着有变化.
//MethodInvocationProceedingJoinPoint的源码
@Override
public Object[] getArgs() {
if (this.args == null) {
this.args = this.methodInvocation.getArguments().clone();
}
return this.args;
}
// 获取请求参数
// 获取请求参数
ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
HttpServletRequest request = null;
Object[] args = null;
if(attributes != null) {
request = attributes.getRequest();
args = point.getArgs();
}
if(args == null){
// 处理直接调用的情况
if(point instanceof MethodInvocationProceedingJoinPoint){
MethodInvocationProceedingJoinPoint miPoint = (MethodInvocationProceedingJoinPoint)point;
log.info(miPoint.getArgs() + "");
args = miPoint.getArgs();
// 转换后使用下级类的getArgs()可以获得内容
}
}
问题解决, 无法拦截的问题网上有解决方案, 但是无参数的问题完全没发现有相关文章. 找到问题写篇文章做点贡献.