首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >如何在异步通知之前或之后访问Spring AOP中的RequestContextHolder

如何在异步通知之前或之后访问Spring AOP中的RequestContextHolder
EN

Stack Overflow用户
提问于 2021-08-14 10:45:32
回答 1查看 200关注 0票数 0

BeforeAspect.java

代码语言:javascript
运行
复制
@Aspect
@Component
@EnableAsync
public class BeforeAspect {

    @Pointcut("@annotation(com.example.demo.api.EventLog)")
    public void eventLogControllers() {}

    @Before("eventLogControllers()")
    @Async
    public void beforeController(JoinPoint BeforeJoinPoint){
        HttpServletRequest requestAttributes=((ServletRequestAttributes) RequestContextHolder.currentRequestAttributes()).getRequest();
        System.out.println("Before LocalName: "+requestAttributes.getLocalName());
        System.out.println("Before Request URL: "+requestAttributes.getRequestURL());
    }
}

Controller.java

代码语言:javascript
运行
复制
@RequestMapping("employee")
@RestController
public class Controller {
    EmployeeService empser;
    @Autowired
    public Controller(EmployeeService empser) {
        this.empser = empser;
    }

    @GetMapping
    @EventLog
    public List<Employee> selectemployees(){
        return empser.findallemployees();
    }
}

EventLog.java

代码语言:javascript
运行
复制
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.METHOD)
public @interface EventLog {
}

当我运行应用程序时,我得到以下错误

代码语言:javascript
运行
复制
java.lang.IllegalStateException: No thread-bound request found: Are you referring to request attributes outside of an actual web request, or processing a request outside of the originally receiving thread? If you are actually operating within a web request and still receive this message, your code is probably running outside of DispatcherServlet: In this case, use RequestContextListener or RequestContextFilter to expose the current request.
    at org.springframework.web.context.request.RequestContextHolder.currentRequestAttributes(RequestContextHolder.java:131) ~[spring-web-5.2.10.RELEASE.jar:5.2.10.RELEASE]
    at com.example.demo.EventAspects.BeforeAspect.beforeController(BeforeAspect.java:37) ~[classes/:na]
    at com.example.demo.EventAspects.BeforeAspect$$FastClassBySpringCGLIB$$e508b82a.invoke(<generated>) ~[classes/:na]
    at org.springframework.cglib.proxy.MethodProxy.invoke(MethodProxy.java:218) ~[spring-core-5.2.10.RELEASE.jar:5.2.10.RELEASE]
    at org.springframework.aop.framework.CglibAopProxy$CglibMethodInvocation.invokeJoinpoint(CglibAopProxy.java:771) ~[spring-aop-5.2.10.RELEASE.jar:5.2.10.RELEASE]
    at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:163) ~[spring-aop-5.2.10.RELEASE.jar:5.2.10.RELEASE]
    at org.springframework.aop.framework.CglibAopProxy$CglibMethodInvocation.proceed(CglibAopProxy.java:749) ~[spring-aop-5.2.10.RELEASE.jar:5.2.10.RELEASE]
    at org.springframework.aop.interceptor.AsyncExecutionInterceptor.lambda$invoke$0(AsyncExecutionInterceptor.java:115) ~[spring-aop-5.2.10.RELEASE.jar:5.2.10.RELEASE]
    at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264) ~[na:na]
    at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1128) ~[na:na]
    at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:628) ~[na:na]
    at java.base/java.lang.Thread.run(Thread.java:834) ~[na:na]

当我试图访问employee api时,我得到了上面的错误。我的要求是,我需要在AOP before通知(Aspectj)中创建异步AOP,并在异步before方法中访问请求细节。如果该方法不是异步的,那么它工作得很好。有没有一种方法可以将RequestContextHolder作为参数传递给之前的方法?或者有没有其他方法可以访问它。

EN

回答 1

Stack Overflow用户

发布于 2021-08-16 03:31:53

我不是Spring用户,但有时会尝试用我的AOP知识来帮助Spring AOP用户。这是关于Spring的@Async特性的更多内容,所以我对此不是很了解。

Here是一些关于异步AOP通知的一般信息,以及关于@Around的额外信息,这似乎不是您关注的重点。但也许你可以从我的答案中提取一些有用的东西。

至于你的用例,你显然是在强迫某些东西是异步的,而这些东西应该是同步的。您只说希望通知异步运行,但没有解释原因。它同步地工作得很好,为什么要费心去破坏一个正常工作的系统呢?你的外貌真的这么慢吗?去优化它吧!

如果您坚持让它异步,为什么不遵循错误消息中给出的建议呢?引用:

代码语言:javascript
运行
复制
No thread-bound request found:

Are you referring to request attributes outside of an actual web request,
or processing a request outside of the originally receiving thread?

If you are actually operating within a web request and still receive this
message, your code is probably running outside of DispatcherServlet:
In this case, use RequestContextListener or RequestContextFilter to expose
the current request.
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/68782538

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档