RxJava、Retrofit接收Error Response Body

栏目: Java · 发布时间: 5年前

内容简介:一个基本的RxJava配合Retrofit以及Lambda的网络调用看起来像这个样子的:当

RxJava 配合 Retrofit 能够大大简化Android项目中的网络请求代码量,使得逻辑更清晰,当然也可能会遇到一些问题。下面给出一种问题的解决方案。

需求

一个基本的RxJava配合Retrofit以及Lambda的网络调用看起来像这个样子的:

Subscription subscription = mApi.getSimpleApi()
       .subscribeOn(Schedulers.io())
       .observeOn(AndroidSchedulers.mainThread())
       .subscribe(response -> {

        //do Something

       }, throwable -> {

       //Ops Error

       });

Retrofit 中的网络请求返回码状态码为 200 时,执行 do Something 中的逻辑处理正常的

业务流程,但是当服务器返回状态码为 非200 时,将会执行 Ops Error 中的业务流程而不会

执行 do Something 中的业务逻辑。

这样本没有什么问题,一般我们会在错误处理逻辑中在UI中给出错误提示,像这样:

Log.e("Ops", "Error:" + throwable.getMessage());

但是这样的话我们只能获取到一服务器的错误响应码以及对应的简短的响应码错误说明,一般情况下我们服务器

都会包装错误信息为一个JSON,客户端解析错误信息必要的时候动态展示在UI上以提示用户。如果我们要拿到这样的JSON,使用 throwable.getMessage() 这样做显然是不行的。是不是使用RxJava配合Retrofit只能拿到这样的错误Throwable信息呢?

显然不是的,其实服务器返回的错误信息 非200 响应码的 Response Body JSON对象包含在这个 throwable 对象中,我们可以这样将其解析出来:

throwable -> {
          if(throwable instanceof HttpException){
            HttpException httpException= (HttpException) throwable;
            try {
              String errorBody= httpException.response().errorBody().string();

		//TODO: parse To JSON Obj

            } catch (IOException e) {
              e.printStackTrace();
            }
          }
	 //Ops Print throwable

        });

Parse to JSON Obj 中将 errorBody 解析为JSON对象进行相应的处理即可。

然而,你不能让我每个地方都加上这样的一段代码吧,既然我们使用的是 RxJava ,我们可以让这种处理稍微看起来优雅点。以下以 Jackson 为例:

自定义Action1

由于 RxJava 的错误异常处理接受一个参数,并且没有返回值,因此我们可以定义一个 Action1 来替代默认的Error Action:

public abstract class ErrorAction implements Action1<Throwable> {

  @Override public void call(Throwable throwable) {
    call(ErrorMessage.handle(throwable));
  }

  public abstract void call(ErrorMessage error);
}

其中 ErrorMessage 为我们定义好的错误消息Model:

定义Throwable Handle

@JsonIgnoreProperties(ignoreUnknown = true) public class ResponseError {
  private final static int ERROR_CODE_IO_ERROR = 2072;
  private final static int ERROR_CODE_UN_KNOW = 2073;
  @JsonProperty("status_code") public int statusCode;
  public String message;

  public void setStatusCode(int statusCode) {
    this.statusCode = statusCode;
  }

  public void setMessage(String message) {
    this.message = message;
  }

  public static ResponseError handle(Throwable throwable) {
    ResponseError responseError = null;
    if (throwable instanceof HttpException) {
      HttpException exception = (HttpException) throwable;
      try {
        responseError = new ObjectMapper().readValue(exception.response().errorBody().string(),
            ResponseError.class);
      } catch (IOException e) {
        responseError = new ResponseError();
        responseError.setMessage(e.getLocalizedMessage());
        responseError.setStatusCode(ERROR_CODE_IO_ERROR);
      }
    } else {
      responseError = new ResponseError();
      responseError.setMessage(throwable.getMessage());
      responseError.setStatusCode(ERROR_CODE_UN_KNOW);
    }
    return responseError;
  }
}

这样,我们就完成了一个自定义 Action1 了,接下来我们便可以这样使用了:

Subscription subscription = mApi.getSimpleApi()
        .subscribeOn(Schedulers.io())
        .observeOn(AndroidSchedulers.mainThread())
        .subscribe(response -> {

         //do Something

        },  new ErrorAction() {
              @Override public void call(ErrorMessage msg) {
			//Do Error               

              }
            });

其中在 Do Error 中拿到 ErrorMessage 对象,进行相应的对象操作即可~

Enjoy IT!


以上所述就是小编给大家介绍的《RxJava、Retrofit接收Error Response Body》,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对 码农网 的支持!

查看所有标签

猜你喜欢:

本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们

孵化Twitter

孵化Twitter

[美]尼克·比尔顿(Nick Bilton) / 欧常智、张宇、单旖 / 浙江人民出版社 / 2014-1 / 49.90元

一个在挣扎中生存的博客平台Odeo,一小撮龙蛇混杂的无政府主义者员工,经历了怎样的涅槃,摇身一变,成为纽交所最闪耀的上市企业Twitter? 一个野心勃勃的农场小男孩,一个满身纹身的“无名氏“,一个爱开玩笑的外交家,一位害羞而又充满活力的极客,这四位各有特色的创始人如何从兢兢业业、每日劳作的工程师,成为了登上杂志封面、奥普拉秀和每日秀的富裕名人?而在Twitter日益茁壮成长的过程中,他们又......一起来看看 《孵化Twitter》 这本书的介绍吧!

XML、JSON 在线转换
XML、JSON 在线转换

在线XML、JSON转换工具

HEX HSV 转换工具
HEX HSV 转换工具

HEX HSV 互换工具

HSV CMYK 转换工具
HSV CMYK 转换工具

HSV CMYK互换工具