【问题标题】:Spring 3.2 @ControllerAdvice Not WorkingSpring 3.2 @ControllerAdvice 不工作
【发布时间】:2013-08-23 05:13:47
【问题描述】:

我无法让@ControllerAdvice 工作。我更新了我的命名空间位置,在我的 xml 文件中是 3.1。我将带有控制器的类移动到与控制器相同的包中。我正在使用 3.2.0 版本的 jar。如果我将@ExceptionHandler 注释放在控制器代码中,它可以工作,但不能在带有@ControllerAdvice 的单独类中。当@ControllerAdvice 类失败时,我会看到未捕获的异常处理程序视图。有人对如何解决这个问题有想法吗?

【问题讨论】:

  • 你能解决这个问题吗?我遇到了和你一样的问题。

标签: spring-mvc exception-handling


【解决方案1】:

如果您使用类路径扫描,可能您必须将新的包含过滤器添加到您的 <context:component-scan> 元素:

<context:include-filter type="annotation" 
    expression="org.springframework.web.bind.annotation.ControllerAdvice" />

默认扫描不查找此注解,遵循 spring-context-3.2.xsd for component-scan:

“扫描类路径以查找将自动注册为 Spring bean 的注释组件。默认情况下,将检测 Spring 提供的 @Component、@Repository、@Service 和 @Controller 构造型。”

【讨论】:

  • 这是有道理的,为什么它不起作用。我今晚会测试它,看看它是否有效。
  • 当心!它开箱即用,但是当您进行单元测试时,此注释是必需的!
  • 还要确保这是在 webmvc 上下文文件中,而不是主应用程序上下文中。
【解决方案2】:

不需要额外的配置。它应该可以工作。查看此链接以获取更多详细信息。这提供了一个非常简单的例子:

【讨论】:

  • 这似乎是真的,尽管测试是一个完全不同的问题。
  • @IlyaSlyisarenko 我修复了断开的链接。
【解决方案3】:

对于这个问题,首先是确认你的配置,

  1. 您需要确保组件扫描基础包下的 @ControllerAdvice 类。
  2. 让你在 spring-servlet.xml 中使用&lt;mvc:annotation-driven/&gt;。或在您的 @ControllerAdvice 类中使用 @EnableWebMvc

当你有正确的配置时,ControllerAdvice 应该已经工作了,现在你说你得到了你的未捕获异常处理程序视图。我猜你在 InegrationTest 中得到了它,并且你使用了 mockMvc 来测试它,如果是这样,你需要把 @WebAppConfiguration 和构建 mokcMvc 如下:

 @Autowired
private WebApplicationContext wac;

mockMvc = MockMvcBuilders.webAppContextSetup(wac).build();

使用standaloneSetup(controller) 将不起作用,因为缺少WebApplicationContext。

【讨论】:

  • 就我而言,@EnableWebMvc 就足够了
  • 也可以在standaloneSetup中添加ControllerAdvice类:MockMvcBuilders.standaloneSetup(new MyController(myService)) .setControllerAdvice(new MyControllerAdvice()).build();
【解决方案4】:

我遇到了同样的问题,我的 @ControllerAdvice 类在单元测试 REST 控制器的异常时无法加载。如果您使用的是 spring boot(版本 4),那么您可以使用 spring 添加的其他方法在独立设置控制器时加载控制器建议类。

mockMvc = MockMvcBuilders
   .standaloneSetup(new YourRestController())
   .setControllerAdvice(new ControllerAdviceClass())
   .build();

这将直接初始化您的控制器建议类,并且您的 Junit 测试应该能够跳转到您的控制器建议类中定义的 @ExceptionHandler 方法。

【讨论】:

  • 天哪,非常感谢!!顺便说一句,您缺少括号。应该是MockMvcBuilders.standaloneSetup(new YourRestController()).setControllerAdvice( ...。注意YourRestController() 后面的括号。
【解决方案5】:

对我来说,@ControllerAdvice 不惜一切代价工作。即使添加@EnableWebMvc@WebAppConfiguration 也没有任何改变。

我能够让它工作的方式是,

  • 为我的AbstractController 类添加@ExceptionHandler 方法,这是所有其他控制器都在扩展的类。

我认为@ControllerAdvice 应该做同样的事情,即将@ControllerAdvice 指定的类下定义的@ExceptionHandler 方法编译到每个控制器都可以引用的公共位置。但不幸的是,它对我不起作用。

【讨论】:

    【解决方案6】:

    我遇到了同样的问题,在我的情况下,问题是有一个依赖库,其中有一个带有 @ControllerAdvice 和 @Order(Ordered.HIGHEST) 注释的类,为了解决这个问题,我添加了 @Order (Ordered.HIGHEST) 注释在我的课堂上,现在它可以工作了。

    由于我的异常类在同一个控制器包中,因此即使两个类具有相同的 @Order(Ordered.HIGHEST),spring 也给了我的类更高的优先级

    @ControllerAdvice
    @Order(Ordered.HIGHEST)
    public class RestResponseEntityExceptionHandler 
      extends ResponseEntityExceptionHandler { 
    

    【讨论】:

    • 或者我们可以注释:@Order(Ordered.HIGHEST_PRECEDENCE)
    【解决方案7】:

    我通过在 Configuration bean 中定义 ControlAdvice 类来解决它,如下所示:

    @Primary 
    @Bean 
    public RestResponseEntityExceptionHandler restResponseEntityExceptionHandler (){    
           return new RestResponseEntityExceptionHandler (); 
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2021-05-22
      • 2017-12-17
      • 1970-01-01
      • 2017-11-06
      • 1970-01-01
      • 1970-01-01
      • 2020-06-05
      • 2023-03-06
      相关资源
      最近更新 更多