自动装配依赖项未注入到 Spring MVC 的 Aspect 中

发布于 2024-12-08 21:28:27 字数 4463 浏览 0 评论 0原文

我无法 @Autowire Aspect 中的服务层实例。在 Aspect 中,对@Autowired bean 的引用为 NULL,并抛出 NullPointerException。任何帮助将不胜感激。我想,我搞砸了配置。

以下是我的 servlet-context.xml

<!-- Activates various annotations to be detected in bean classes -->
<context:annotation-config />
<context:spring-configured />       

<!-- Scans the classpath of this application for @Components to deploy as beans -->
<context:component-scan base-package="xx.yy" />

<!--  an @AspectJ aspect will be interpreted as an aspect by Spring AOP and beans in the context will be advised accordingly -->
<aop:aspectj-autoproxy />

<beans:bean id="loggingAspect" class="xx.yy.aop.aspects.LoggingAspect" />
<beans:bean id="authenticationAspect" class="xx.yy.aop.aspects.AuthenticationAspect" />

<!-- Enables the Spring MVC @Controller programming model -->
<annotation-driven />

以下是我的方面:

@Configurable
@Component
@Aspect
public class AuthenticationAspect {
private static final Logger logger = LoggerFactory.getLogger(AuthenticationAspect.class);

@Autowired
private LoginService loginService;

    //.... 
}

这是我的控制器,使用上面定义的 @Authentication 注释:

@Controller
@RequestMapping("/user")
public class UsersController {

@Autowired
private UserService userService;

@Authenticate
@RequestMapping(value="/{userId}/profile", method=RequestMethod.GET)    
public String displayUser(WebRequest webRequest, @PathVariable("userId") String userId, Model model) {
    User user = userService.findUser(Long.valueOf(userId));  
    model.addAttribute("user", user);
    model.addAttribute("AccordionMenuTab","5");
    model.addAttribute("selectedLink","profile");
    return "profile";
}

我收到以下异常:

Oct 8, 2011 3:12:48 AM org.apache.catalina.core.StandardWrapperValve invoke
SEVERE: Servlet.service() for servlet appServlet threw exception
java.lang.NullPointerException
    at xx.yy.controller.UsersController.displayUser_aroundBody1$advice(UsersController.java:28)
    at xx.yy.controller.UsersController.displayUser(UsersController.java:1)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    at java.lang.reflect.Method.invoke(Method.java:597)
    at org.springframework.web.bind.annotation.support.HandlerMethodInvoker.invokeHandlerMethod(HandlerMethodInvoker.java:176)
    at org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter.invokeHandlerMethod(AnnotationMethodHandlerAdapter.java:426)
    at org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter.handle(AnnotationMethodHandlerAdapter.java:414)
    at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:790)
    at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:719)
    at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:644)
    at org.springframework.web.servlet.FrameworkServlet.doGet(FrameworkServlet.java:549)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:617)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:717)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
    at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:233)
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:191)
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:127)
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102)
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109)
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:298)
    at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:859)
    at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:588)
    at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:489)
    at java.lang.Thread.run(Thread.java:662)

I am not able to @Autowire the Service Layer Instance in Aspect. In Aspect the reference to the @Autowired bean is NULL and it throws NullPointerException. Any help will be much appreciated. I think, I messed up with configuration.

Following is my servlet-context.xml:

<!-- Activates various annotations to be detected in bean classes -->
<context:annotation-config />
<context:spring-configured />       

<!-- Scans the classpath of this application for @Components to deploy as beans -->
<context:component-scan base-package="xx.yy" />

<!--  an @AspectJ aspect will be interpreted as an aspect by Spring AOP and beans in the context will be advised accordingly -->
<aop:aspectj-autoproxy />

<beans:bean id="loggingAspect" class="xx.yy.aop.aspects.LoggingAspect" />
<beans:bean id="authenticationAspect" class="xx.yy.aop.aspects.AuthenticationAspect" />

<!-- Enables the Spring MVC @Controller programming model -->
<annotation-driven />

Following is my Aspect:

@Configurable
@Component
@Aspect
public class AuthenticationAspect {
private static final Logger logger = LoggerFactory.getLogger(AuthenticationAspect.class);

@Autowired
private LoginService loginService;

    //.... 
}

Here is my controller using the @Authentication Annotation defined above:

@Controller
@RequestMapping("/user")
public class UsersController {

@Autowired
private UserService userService;

@Authenticate
@RequestMapping(value="/{userId}/profile", method=RequestMethod.GET)    
public String displayUser(WebRequest webRequest, @PathVariable("userId") String userId, Model model) {
    User user = userService.findUser(Long.valueOf(userId));  
    model.addAttribute("user", user);
    model.addAttribute("AccordionMenuTab","5");
    model.addAttribute("selectedLink","profile");
    return "profile";
}

I am getting following exception:

Oct 8, 2011 3:12:48 AM org.apache.catalina.core.StandardWrapperValve invoke
SEVERE: Servlet.service() for servlet appServlet threw exception
java.lang.NullPointerException
    at xx.yy.controller.UsersController.displayUser_aroundBody1$advice(UsersController.java:28)
    at xx.yy.controller.UsersController.displayUser(UsersController.java:1)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    at java.lang.reflect.Method.invoke(Method.java:597)
    at org.springframework.web.bind.annotation.support.HandlerMethodInvoker.invokeHandlerMethod(HandlerMethodInvoker.java:176)
    at org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter.invokeHandlerMethod(AnnotationMethodHandlerAdapter.java:426)
    at org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapter.handle(AnnotationMethodHandlerAdapter.java:414)
    at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:790)
    at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:719)
    at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:644)
    at org.springframework.web.servlet.FrameworkServlet.doGet(FrameworkServlet.java:549)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:617)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:717)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
    at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:233)
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:191)
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:127)
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102)
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109)
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:298)
    at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:859)
    at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:588)
    at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:489)
    at java.lang.Thread.run(Thread.java:662)

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

绝不放开 2024-12-15 21:28:27

请参阅 这篇文章文档

7.8.3 使用 Spring IoC 配置 AspectJ 方面

当在 Spring 应用程序中使用 AspectJ 方面时,很自然地希望并期望能够使用 Spring 配置这些方面。 AspectJ 运行时本身负责切面创建,并且通过 Spring 配置 AspectJ 创建的切面的方式取决于切面使用的 AspectJ 实例化模型(“per-xxx”子句)。

大多数 AspectJ 方面都是单例方面。这些方面的配置非常简单:只需创建一个像平常一样引用方面类型的 bean 定义,并包含 bean 属性“factory-method="aspectOf"”。这确保 Spring 通过向 AspectJ 请求来获取切面实例,而不是尝试自己创建实例。例如:

<bean id="profiler" class="com.xyz.profiler.Profiler"
      factory-method="aspectOf" />

See this piece of the documentation:

7.8.3 Configuring AspectJ aspects using Spring IoC

When using AspectJ aspects with Spring applications, it is natural to both want and expect to be able to configure such aspects using Spring. The AspectJ runtime itself is responsible for aspect creation, and the means of configuring the AspectJ created aspects via Spring depends on the AspectJ instantiation model (the 'per-xxx' clause) used by the aspect.

The majority of AspectJ aspects are singleton aspects. Configuration of these aspects is very easy: simply create a bean definition referencing the aspect type as normal, and include the bean attribute 'factory-method="aspectOf"'. This ensures that Spring obtains the aspect instance by asking AspectJ for it rather than trying to create an instance itself. For example:

<bean id="profiler" class="com.xyz.profiler.Profiler"
      factory-method="aspectOf" />
凉城 2024-12-15 21:28:27

对于任何寻找基于 java 的 bean 配置的人,使用 java 反射我可以归档相同的内容

@Bean
public ExceptionAspectHandler exceptionAspectHandler(){
    try
    {
        //noinspection JavaReflectionMemberAccess
        Method method = ExceptionAspectHandler.class.getMethod("aspectOf" );
        return (ExceptionAspectHandler) method.invoke(null);
    }
    catch( IllegalAccessException | InvocationTargetException | NoSuchMethodException e )
    {
       logger.log( Level.SEVERE, "Error creating bean : ", e );
    }
    return null;
}

,因为 aspectOf() 方法在编译时不可用,我们无法通过仅调用该方法来创建 bean。这就是 XML 配置能够处理它的原因。

另一种更简单的方法

@Bean
public ExceptionAspectHandler exceptionAspectHandler()
{
    return Aspects.aspectOf( ExceptionAspectHandler.class );
}

这也可行。

For anyone looking for a java based bean configuration, Using java reflections I could archive the same

@Bean
public ExceptionAspectHandler exceptionAspectHandler(){
    try
    {
        //noinspection JavaReflectionMemberAccess
        Method method = ExceptionAspectHandler.class.getMethod("aspectOf" );
        return (ExceptionAspectHandler) method.invoke(null);
    }
    catch( IllegalAccessException | InvocationTargetException | NoSuchMethodException e )
    {
       logger.log( Level.SEVERE, "Error creating bean : ", e );
    }
    return null;
}

Since the aspectOf() method is not available during compile time we cannot create the bean by just calling the method. That is why XML configuration is able to handle it.

Alternatively simpler approach

@Bean
public ExceptionAspectHandler exceptionAspectHandler()
{
    return Aspects.aspectOf( ExceptionAspectHandler.class );
}

This also does work.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文