@Around advice doesn't work with OncePerRequestFilter
See original GitHub issueAffects: Spring Boot 2.5.6 (Both AOP and Web are 2.5.6)
Greetings,
I’m relatively new to Spring, but after a bit of Googling this seems like an issue with interconnection between different Spring components. Or maybe I’m just using them wrong? Please advise if so, otherwise this just might be an unfortunate bug?
I’m trying to add a traceId entry to our logs via MDC.
I’ve created a filter that extends OncePerRequestFilter
which doesn’t really do anything, except serves as a place to attach an advice to.
@Component
class TraceIdFilter : OncePerRequestFilter() {
@Traceable
override fun doFilterInternal(
request: HttpServletRequest,
response: HttpServletResponse,
filterChain: FilterChain
) {
filterChain.doFilter(request, response)
}
}
I have an @Around
advice:
@Aspect
@Component
class TraceableRequestAspect(private val uuid: () -> UUID) {
@Around("@annotation(Traceable)")
fun advice(joinPoint: ProceedingJoinPoint) {
try {
MDC.put(LogstashField.TRACE_ID, "${uuid()}")
joinPoint.proceed()
} finally {
MDC.remove(LogstashField.TRACE_ID)
}
}
}
I expect that the Around advice will ‘wrap’ the filter method and attach an MDC entry to all HTTP request logs and then clean up after itself.
In reality, this is what I’m seeing:
2022-01-20 14:42:54.147 INFO 23739 --- [ main] o.s.aop.framework.CglibAopProxy : Unable to proxy interface-implementing method [public final void org.springframework.web.filter.OncePerRequestFilter.doFilter(javax.servlet.ServletRequest,javax.servlet.ServletResponse,javax.servlet.FilterChain) throws javax.servlet.ServletException,java.io.IOException] because it is marked as final: Consider using interface-based JDK proxies instead!
2022-01-20 14:42:54.147 INFO 23739 --- [ main] o.s.aop.framework.CglibAopProxy : Unable to proxy interface-implementing method [public final void org.springframework.web.filter.GenericFilterBean.init(javax.servlet.FilterConfig) throws javax.servlet.ServletException] because it is marked as final: Consider using interface-based JDK proxies instead!
2022-01-20 14:42:54.211 ERROR 23739 --- [ main] o.a.c.c.C.[Tomcat].[localhost].[/] : Exception starting filter [traceIdFilter]
java.lang.NullPointerException: null
at org.springframework.web.filter.GenericFilterBean.init(GenericFilterBean.java:241)
at org.apache.catalina.core.ApplicationFilterConfig.initFilter(ApplicationFilterConfig.java:270)
at org.apache.catalina.core.ApplicationFilterConfig.<init>(ApplicationFilterConfig.java:105)
at org.apache.catalina.core.StandardContext.filterStart(StandardContext.java:4613)
at org.apache.catalina.core.StandardContext.startInternal(StandardContext.java:5256)
at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:183)
at org.apache.catalina.core.ContainerBase$StartChild.call(ContainerBase.java:1396)
at org.apache.catalina.core.ContainerBase$StartChild.call(ContainerBase.java:1386)
at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264)
at org.apache.tomcat.util.threads.InlineExecutorService.execute(InlineExecutorService.java:75)
at java.base/java.util.concurrent.AbstractExecutorService.submit(AbstractExecutorService.java:140)
at org.apache.catalina.core.ContainerBase.startInternal(ContainerBase.java:919)
at org.apache.catalina.core.StandardHost.startInternal(StandardHost.java:835)
at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:183)
at org.apache.catalina.core.ContainerBase$StartChild.call(ContainerBase.java:1396)
at org.apache.catalina.core.ContainerBase$StartChild.call(ContainerBase.java:1386)
at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264)
at org.apache.tomcat.util.threads.InlineExecutorService.execute(InlineExecutorService.java:75)
at java.base/java.util.concurrent.AbstractExecutorService.submit(AbstractExecutorService.java:140)
at org.apache.catalina.core.ContainerBase.startInternal(ContainerBase.java:919)
at org.apache.catalina.core.StandardEngine.startInternal(StandardEngine.java:263)
at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:183)
at org.apache.catalina.core.StandardService.startInternal(StandardService.java:432)
at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:183)
at org.apache.catalina.core.StandardServer.startInternal(StandardServer.java:927)
at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:183)
at org.apache.catalina.startup.Tomcat.start(Tomcat.java:486)
at org.springframework.boot.web.embedded.tomcat.TomcatWebServer.initialize(TomcatWebServer.java:123)
at org.springframework.boot.web.embedded.tomcat.TomcatWebServer.<init>(TomcatWebServer.java:104)
at org.springframework.boot.web.embedded.tomcat.TomcatServletWebServerFactory.getTomcatWebServer(TomcatServletWebServerFactory.java:450)
at org.springframework.boot.web.embedded.tomcat.TomcatServletWebServerFactory.getWebServer(TomcatServletWebServerFactory.java:199)
at org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext.createWebServer(ServletWebServerApplicationContext.java:182)
at org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext.onRefresh(ServletWebServerApplicationContext.java:160)
at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:577)
at org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext.refresh(ServletWebServerApplicationContext.java:145)
at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:754)
at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:434)
at org.springframework.boot.SpringApplication.run(SpringApplication.java:338)
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1343)
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1332)
at net.leoncorp.ft.integration.ApplicationKt.main(Application.kt:14)
2022-01-20 14:42:54.212 ERROR 23739 --- [ main] o.apache.catalina.core.StandardContext : One or more Filters failed to start. Full details will be found in the appropriate container log file
2022-01-20 14:42:54.212 ERROR 23739 --- [ main] o.apache.catalina.core.StandardContext : Context [] startup failed due to previous errors
2022-01-20 14:42:54.254 INFO 23739 --- [ main] o.apache.catalina.core.StandardService : Stopping service [Tomcat]
I’m not sure whether I can follow the advice the error message throws as none of the code responsible for this is under my purview.
Thanks in advance for any assistance.
Issue Analytics
- State:
- Created 2 years ago
- Comments:10 (6 by maintainers)
I opened #27980 to address this.
For reference: This question has been asked again lately on Stack Overflow, and here is my answer explaining the situation in more detail, also linking back to @mdeinum’s reply here. The more general issue with trying to advise final methods accessing instance fields is explained here. My answer on SO also contains sample pointcuts for users who want to do advise filters using native AspectJ.