我正在尝试根据 HTTP 状态代码显示自定义错误页面。我所做的是实现 Spring 的 ErrorController
CustomErrorController
中的接口(interface)但似乎 Spring Boot 没有识别它。
我已按照本教程执行此操作:https://www.baeldung.com/spring-boot-custom-error-page (第 3.1 节)。
我已经读过,首先你需要摆脱著名的 Spring 的默认 Whitelabel 错误页面。所以我这样做了:
@SpringBootApplication(exclude = { ErrorMvcAutoConfiguration.class })
public class MyApplication {
public static void main(String[] args) {
SpringApplication.run(MyApplication.class, args);
}
}
这似乎有效,因为 Whitelabel 错误页面不再出现,但现在当发生错误时,Apache Tomcat 错误页面(包含堆栈跟踪的丑陋页面)出现而不是我的。
然后我刚刚实现了我的
CustomErrorController
像这样:@Controller
@RequestMapping("/error")
public class CustomErrorController implements ErrorController {
@RequestMapping
public String handleError(HttpServletRequest request) {
Integer statusCode = (Integer) request.getAttribute(RequestDispatcher.ERROR_STATUS_CODE);
if (statusCode != null) {
// Specific error page
return "redirect:/error/" + statusCode;
}
// Global error page
return "error/error";
}
@Override
public String getErrorPath() {
return "/error";
}
@GetMapping("/404")
public String notFoundErrorPage() {
return "error/404";
}
// Other error codes mapping methods
}
我正在使用 Thymeleaf,我的错误 View 位于
src/main/resources/views/error
下,其中每个特定的错误页面名称都遵循 <error_code>.html
的推荐格式因此,例如,404 错误将具有 404.html
关联的页面。到目前为止,我在解决其他应用程序 View 方面没有任何问题。实际上,我已将 Spring Security 配置为调用
/error/403
如果发生访问被拒绝并且错误页面正确显示,则端点。/error/500
也是如此,当发生内部服务器异常时调用它,因为我还实现了以下 @ControllerAdvice @ExceptionHandler
方法:@ControllerAdvice
@Log4j2
public class GlobalDefaultExceptionHandler {
@ExceptionHandler(Exception.class)
public String defaultErrorHandler(Exception exception) throws Exception {
if (AnnotationUtils.findAnnotation(exception.getClass(), ResponseStatus.class) != null) {
throw exception;
}
log.catching(exception);
return "redirect:/error/500";
}
}
因此,如果这些端点中的每一个都单独工作,为什么如果 Spring 抛出错误
handleError
方法没有被调用过吗?谢谢你。
最佳答案
好像你的 GlobalDefaultExceptionHandler
正在预先捕获每个异常。这就是为什么handleError
永远不会被调用。
您的其他端点工作,因为您直接调用它们 - 正如您所描述的那样。
我建议使用 @ControllerAdvice
处理特定异常让您的CustomErrorController
实现处理所有尚未处理的异常。 Spring Boot 会将它们包裹在 NestedServletException
内使用 Http Status 500。您可以在 handleError
中找到根本原因和:
Object exception = request.getAttribute("javax.servlet.error.exception");
if (String.valueOf(exception) != null) {
log.info("Nested Exception: " + String.valueOf(exception));
}
检查这些答案以获取有关订购和 Spring Boot 中的错误工作流程的更多信息:
order
spring boot error handling flow
关于Spring Boot 不显示实现自定义 ErrorController 的错误页面,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56061542/