RestExceptionHandler 就本示例代码中,就只是一个 CustomizedBaseExceptionHandler 的空子类了。
@ControllerAdvice
@RestController
public class RestExceptionHandler extends CustomizedBaseExceptionHandler {
}
如果要为某个特定的异常添加处理逻辑,可以在该处理器类中实现,实现方式请参考 ResponseEntityExceptionHandler 和 CustomizedBaseExceptionHandler。
关于该业务模块,还有最后两点值得一提,那就是对于『Not Found』和 『参数校验』的处理方式。
『Not Found』,在 RESTful 风格的 API 中是一个很值得推敲的技巧点。在 RFC 规范定义了 HTTP 404 这个响应状态码,用于描述 "Not Found" 错误。在以模板视图为返回内容的 Web MVC 中,该状态码表示访问的视图资源未找到,说明访问路径有误。而在以无状态的资源未返回内容的接口风格中,除了访问路径有误这一种原因外,还可能路径虽然没有问题,但资源在服务器上不存在了。
比如 GET/books/1 或者 PUT/books/1 以及 /books/foobar 虽然从形式上来看,这三种也都勉强可以归类为路径不存在,但其实前两者和第三个的本质上是不同的,前两者匹配的是路径 /books/{id},这里只是代表 id 为 1 的资源在服务器上不存在了,而 /books/foobar 则是在服务器上根本未定义这样的一个资源路径。
对于这种情况,我们认为一个好的处理方式是,把第三种当做 HTTP 404 处理,即客户端访问了错误的资源路径,而把路径模式正确而资源可能因为已删除或未添加等原因导致的资源未找到,对应到 HTTP 400 状态码上,认为是客户端只是请求参数有问题,以至于请求到了不存在的资源。Spring WebMVC 默认会把未定义 RequestMapping 的路径使用默认的映射器处理器处理,把它当做是对静态资源的请求,从而给出一个 404 的错误响应状态。我们在 application.properties 中通过设置 spring.mvc.throw-exception-if-no-handler-found=true 和 spring.resources.add-mappings=false