经验首页 前端设计 程序设计 Java相关 移动开发 数据库/运维 软件/图像 大数据/云计算 其他经验
当前位置:技术经验 » Java相关 » Java » 查看文章
dubbo~全局异常拦截器的使用与设计缺陷~续
来源:cnblogs  作者:张占岭  时间:2024/6/11 9:45:52  对本文有异议

上一次的介绍,主要围绕如何统一去捕获异常,以及为每一种异常添加自己的Mapper实现,并且我们知道,当在ExceptionMapper中返回非200的Response,不支持application/json的响应类型,而是写死的text/plain类型。

Filter为二方包异常手动捕获

参考:https://blog.csdn.net/2401_84048290/article/details/138105184

我们来看看dubbo的源码进行分析,如果Dubbo的provider端 抛出异常(Throwable),则会被 provider端 的ExceptionFilter拦截到,执行以下invoke方法,里面有个实现Listener类,重写了onResponse,我们可以自定义filter来覆盖原来的ExceptionFilter,把自定义的异常通过RuntimeException进行包裹,然后在Mapper中进行统一的捕获。

  • 添加CustomExceptionFilter类型,实现Filter和BaseFilter.Listener,重写onResponse方法,添加自定义代码,如下:
  1. public class CustomExceptionFilter implements Filter, BaseFilter.Listener {
  2. public void onResponse(Result appResponse, Invoker<?> invoker, Invocation invocation) {
  3. exception = appResponse.getException();
  4. String className = exception.getClass().getName();
  5. // 本项目的异常也直接抛出
  6. if (className.startsWith("com.myself.")) {
  7. appResponse.setException(new RuntimeException(exception));
  8. return;
  9. }
  10. // 其它原来ExceptionFilter中的代码
  11. }
  12. }
  • META-INF中注册这个过滤器resources/META-INF/dubbo/org.apache.dubbo.rpc.Filter
  1. customExceptionFilter=com.xxx.register.exception.filter.CustomExceptionFilter
  • 配置中文中注册,并移除默认的resources/application.properties
  1. # 自定义过滤器,上面-exception就是dubbo默认的处理异常的filter,前面-号就代表去除,注意:不需要加双引号
  2. dubbo.provider.filter=customExceptionFilter,-exception

一个Mapper处理所有自定义异常

  • 配置文件中指定mapper,resources/application.properties
  1. dubbo.protocols.http.extension=com.xxx.register.exception.mapper.CustomExceptionMapper
  • mapper源码如下
  1. @Provider
  2. public class DbViolationExceptionMapper implements ExceptionMapper<RuntimeException> {
  3. @Override
  4. public Response toResponse(RuntimeException exception) {
  5. Map<String, String> map = MapUtil.<String, String>builder().put("error", exception.getMessage()).build();
  6. if (exception.getCause() instanceof ForbiddenException) {
  7. return Response.status(Response.Status.FORBIDDEN).entity(map).type(MediaType.APPLICATION_JSON).build();
  8. }
  9. if (exception.getCause() instanceof CustomException) {
  10. return Response.status(Response.Status.BAD_REQUEST).entity(map).type(MediaType.APPLICATION_JSON).build();
  11. }
  12. if (exception.getCause() instanceof IdentityBrokerException) {
  13. return Response.status(Response.Status.UNAUTHORIZED).entity(map).type(MediaType.APPLICATION_JSON).build();
  14. }
  15. if (exception.getCause() instanceof UniqueException) {
  16. return Response.status(Response.Status.SERVICE_UNAVAILABLE).entity(map).type(MediaType.APPLICATION_JSON)
  17. .build();
  18. }
  19. return Response.status(Response.Status.SERVICE_UNAVAILABLE)
  20. .entity(MapUtil.builder().put("error", exception.getMessage()).build()).type(MediaType.APPLICATION_JSON)
  21. .encoding("utf-8").build();// 非200的请求,这个type无效,一直是text/plain
  22. }
  23. }

未解决的问题

  • 目前非200的请求,toResponse时,响应类型还是text/plain

原文链接:https://www.cnblogs.com/lori/p/18241517

 友情链接:直通硅谷  点职佳  北美留学生论坛

本站QQ群:前端 618073944 | Java 606181507 | Python 626812652 | C/C++ 612253063 | 微信 634508462 | 苹果 692586424 | C#/.net 182808419 | PHP 305140648 | 运维 608723728

W3xue 的所有内容仅供测试,对任何法律问题及风险不承担任何责任。通过使用本站内容随之而来的风险与本站无关。
关于我们  |  意见建议  |  捐助我们  |  报错有奖  |  广告合作、友情链接(目前9元/月)请联系QQ:27243702 沸活量
皖ICP备17017327号-2 皖公网安备34020702000426号