【问题标题】:why Spring boot AspectJ missed to trigger sometimes only为什么 Spring boot AspectJ 有时只错过触发
【发布时间】:2020-05-18 13:23:17
【问题描述】:

我有 Spring 启动应用程序 AspectJ 配置为在一项服务返回数据后异步工作但这仅在某个时候无法触发没有错误记录没有警告,这种情况随时可能发生,如果我错过了任何配置,请告诉我?

应用代码

@SpringBootApplication
@EnableAspectJAutoProxy
@EnableAsync
public class TitlesCompareUtilityApplication {

    public static void main(String[] args) {
        SpringApplication.run(TitlesCompareUtilityApplication.class, args);
    }

}

方面代码

@Aspect
@Component
public class DistributedLoggingAspect {

    private static Logger log = LoggerFactory.getLogger(DistributedLoggingAspect.class);

    @Async
    @AfterReturning("execution(* com.mycomp.repo.TyRepository.findById(..))")
    public void logAfterReturn(JoinPoint joinPoint) {
        int id = (int) joinPoint.getArgs()[0];
        log.info("logAfterReturn() is running! id:{}", id);
    }
}

【问题讨论】:

  • 在我的本地验证中按预期工作。您如何确认方面有时无法触发?请提供minimal reproducible example
  • 正如我所提到的,这种情况很少发生,我无法重现它
  • 您如何确认方面有时无法触发? @Around 建议类型提供更多控制权,可以帮助您调试
  • 没有看到aspect logAfterReturn的日志但是在服务中执行成功,
  • 只要它不能在不同的机器上随意复制,并且没有附加证据来证明遗漏了建议的方面,就很难评论可能发生的事情。如果你有一个可重现的测试用例,你可以将它作为一个 bug 报告给 spring 团队。

标签: spring spring-boot java-8 aspectj spring-aspects


【解决方案1】:

由于技术原因,我发现它极不可能,甚至几乎不可能,有时会错过建议执行,因为当调用公共 Spring bean/组件方法并且存在 AOP 代理时,该代理将拦截方法调用,除非您执行自调用(类内部方法调用)。建议是在同一个线程还是在异步线程中执行(如果可能的话),应该无关紧要。

相反,由于您的应用程序的异步特性,日志条目没有按照您期望的顺序出现,或者在高负载情况下您的记录器缓冲区溢出(取决于您的配置)并记录消息在写入之前就丢失了。

【讨论】:

  • 我在整个日志文件中搜索并没有找到日志,我认为您提到的第二个原因可能是,生成了巨大的日志我将检查记录器缓冲区设置它是默认配置为现在
  • 那是缺少完整MCVE的问题:人们——包括我在内——不得不推测。这意味着,他们可能是错的。也许我是,也许不是。
猜你喜欢
  • 2019-09-15
  • 1970-01-01
  • 2023-02-08
  • 2023-03-07
  • 1970-01-01
  • 2019-05-10
  • 2018-04-09
  • 1970-01-01
  • 2013-12-04
相关资源
最近更新 更多