资讯专栏INFORMATION COLUMN

深入RxEasyHttp网络库教你3分钟学会自定义数据结构

Charles / 2611人阅读

摘要:而本库就想让你通过简单的改造,快速的接入,满足你的数据结构解析,所以提出了自定义数据结构的概念。注意自定义类时其中必须写举列服务器返回的结构是和默认的标准结构一模一样,只是码为表示成功,而库中表示成功。

github源码地址:https://github.com/zhou-you/RxEasyHttp RxEasyHttp库默认ApiResult简介

在自定义ApiResult之前,先了解本库中默认提供的ApiResult方式,包含code、msg、data三个字段,其中默认code为0表示解析成功,内部是用ApiResult进行数据解析的。
默认ApiResult如下:

public class ApiResult {
    private int code;//服务器返回的状态码
    private String msg;//服务器返回的成功/失败信息
    private T data;//返回的真实数据,也是上层在页面需要展示的信息
    public int getCode() {
        return code;
    }
    public void setCode(int code) {
        this.code = code;
    }
    public String getMsg() {
        return msg;
    }
    public void setMsg(String msg) {
        this.msg = msg;
    }
    public T getData() {
        return data;
    }
    public void setData(T data) {
        this.data = data;
    }
    public boolean isOk() {
    //请求成功的判断方法,例如如果指定了code==0是成功,才会回调onSuccess(T t),那么code的非0其它数值都会走失败onError(ApiException e)
        return code == 0 ? true : false;
    }
}

返回正确的json数据:

返回错误的json数据:

code:服务器返回的状态码
msg:服务器返回的成功/失败信息
data:返回的真实数据,也是上层在页面需要展示的信息
isOk():请求成功的判断方法,例如指定了code==0是成功才会回调onSuccess(T t),那么code的其它数值都会走失败onError(ApiException e)
为什么需要自定义ApiResult

每个公司后台都有自己的一套数据结构规范,数据规范基本都会包含code码,错误信息、返回的数据data。但是他们的字段不一定是code、msg、data这样的三个字段。例如你的结构是error_code(code)、reason(msg)、result(data),那这样就会导致解析失败。而又不想因为几个字段的数据结构不一样,所有的解析和业务逻辑重新写一遍。而本库就想让你通过简单的改造,快速的接入,满足你的数据结构解析,所以提出了自定义数据结构的概念。

注:如果服务器人员在写接口时比较随意完全没有规范或者没有code、msg这样的结构,直接就是个bean,本库就不支持后期可以考虑支持,暂时没有提供针对非ApiResult结构的支持

自定义ApiResult原理

ApiResult类中包含code、msg、data的get和set方法,以覆盖重写的方式来解决,在自定义之前需要先用自己的数据结构对比库中默认的数据结构,一样的不用重复添加或者覆写。最主要的是覆写getCode()、getMsg()、getData()、isOk()四个方法,但不是这四个方法都必须全部覆写看看不一致的地方,哪些不一致就覆写哪些,set相关方法不用覆写。主要解决思想就是把不一致的数据结构,改造成和库中默认的结构一致或者靠拢。

注意:自定义ApiResult类时TestApiResult extends ApiResult   其中必须写

举列1:服务器返回的结构是和默认的标准结构一模一样,只是code码为1表示成功,而库中0表示成功。那么只需要覆写isOk()

public class TestApiResult extends ApiResult {
    @Override
    public boolean isOk() {
        return getCode()==1;//code等于1表示成功,所有覆写isOk()
    }
}

举列2:服务器返回的结构是error_code、reason、result和默认的标准结构完全不一样

public class TestApiResult extends ApiResult {
    int error_code; //对应默认标准ApiResult的code
    String reason;//对应默认标准ApiResult的msg
    T result;//对应默认标准ApiResult的data

    @Override
    public T getData() {//因为库里使用data字段,而你的结构是result,所以覆写getData()方法,setData()方法不用覆写
        return result;
    }

    @Override
    public String getMsg() {//因为库里使用msg字段,而你的结构是reason,所以覆写getMsg()方法,setMsg()方法不用覆写
        return reason;
    }

    @Override
    public int getCode() {//因为库里使用code字段,而你的结构是error_code,所以覆写getCode()方法,setCode()方法不用覆写
        return error_code;
    }

    @Override
    public boolean isOk() {//因为库里使用code字段,code==0表示成功,但是你的数据结构是error_code==0,所以覆写isOk(),用error_code==0做为判断成功的条件
        return error_code == 0;//表示成功
    }
}

举列3:服务器返回的结构是no,msg,obj结构,其中msg是一样的就不用再特殊处理,no、obj不一样需要处理

注:其它更多情景自己举一反三
自定义ApiResult请求网络步骤

假如你的请求链接是:
http://japi.juhe.cn/joke/content/list.from?key=f5236a9fb8fc75fac0a4d9b8c27a4e90&page=1&pagesize=10&sort=asc&time=1418745237

第一步:分析数据结构

如果返回的字符串不好查看结构,可以使用工具分析,例如json格式化工具sojson、bejson、Chrome浏览器插件JSON-Handle、Json Viewer等
链接返回的json数据:

第二步:自定义数据结构

看到上面返回的json格式,结合自定义ApiResult原理,定义结构如下:

public class TestApiResult extends ApiResult {
    int error_code; //对应默认标准ApiResult的code
    String reason;//对应默认标准ApiResult的msg
    T result;//对应默认标准ApiResult的data
    @Override
    public T getData() {
        return result;
    }
    @Override
    public String getMsg() {
        return reason;
    }
    @Override
    public int getCode() {
        return error_code;
    }
    @Override
    public boolean isOk() {
        return error_code == 0;//表示成功
    }
}

注:定义出的TestApiResult属于公共的,同样的数据结构都可以使用到

第三步:准备数据解析的result

自定义数据结构TestApiResult是个通用的结构,实体的data是result,result是泛型T,具体表示什么,需要你自己查看返回json结构,本例中result字段中包含一个data字段,data字段是集合,所以如下:

public class Data {
    private String content;
    private String hashId;
    private int unixtime;
    private String updatetime;
    public String getContent() {
        return content;
    }
    public Data setContent(String content) {
        this.content = content;
        return this;
    }
    public String getHashId() {
        return hashId;
    }

    public Data setHashId(String hashId) {
        this.hashId = hashId;
        return this;
    }
    public int getUnixtime() {
        return unixtime;
    }
    public Data setUnixtime(int unixtime) {
        this.unixtime = unixtime;
        return this;
    }
    public String getUpdatetime() {
        return updatetime;
    }

    public Data setUpdatetime(String updatetime) {
        this.updatetime = updatetime;
        return this;
    }

    @Override
    public String toString() {
        return "Data{" +
                "content="" + content + """ +
                ", hashId="" + hashId + """ +
                ", unixtime=" + unixtime +
                ", updatetime="" + updatetime + """ +
                "}";
    }
}
public class Result {
    private List data;
    public void setData(List data) {
        this.data = data;
    }
    public List getData() {
        return data;
    }

    @Override
    public String toString() {
        return "Result{" +
                "data=" + data +
                "}";
    }
}
第四步:网络请求数据

自定义的网络请求必须用回调代理execute(CallBackProxy, T> proxy)来请求网络

EasyHttp.get("http://japi.juhe.cn/joke/content/list.from")
                .params("key", "f5236a9fb8fc75fac0a4d9b8c27a4e90")
                .params("page", "1")
                .params("pagesize", "10")
                .params("sort", "asc")
                .params("time", "1418745237")
                .execute(new CallBackProxy, Result>(new ProgressDialogCallBack(mProgressDialog) {
                    @Override
                    public void onError(ApiException e) {
                        super.onError(e);
                        showToast(e.getMessage());
                    }

                    @Override
                    public void onSuccess(Result result) {
                        if (result != null) showToast(result.toString());
                    }
                }) {
                });
注:通过以上四个步骤就完成了自定义数据结构网络请求数据,是不是觉得写法会有点长,CallBackProxy的泛型参数每次都需要填写,其中TestApiResult是继承ApiResult的,对于一个实际项目来讲后台的服务器数据结构是固定的,也就是TestApiResult是固定的,这种方法太麻烦了,那有没有简单的写法,而又不破坏库的使用方式,请看自定义ApiResult高级用法。
自定义ApiResult高级用法

上面已经提到过使用自定义网络请求必须要用new CallBackProxy, Result>,会有很多重复的操作,结合上面我们看下如何简写。讲解之前先说下库中实现方式,网络请求EasyHttp.get()是返回一个GetRequest请求,EasyHttp.post()是返回一个PostRequest请求.如果想让所有的请求execute()方法都自动加上new CallBackProxy, T>,就需要修改execute()方法,而execute()方法是在GetRequest和PostRequest中,所以我们需要分别继承GetRequest和PostRequest,重写execute()方法。具体操作如下:

自定义GetRequest请求

注:下面代码可以直接拷贝过去使用,其中的TestApiResult修改成自己的ApiResult就可以了

public class CustomGetRequest extends GetRequest {
    public CustomGetRequest(String url) {
        super(url);
    }

    @Override
    public  Observable execute(Type type) {
        return super.execute(new CallClazzProxy, T>(type) {
        });
    }

    @Override
    public  Observable execute(Class clazz) {
        return super.execute(new CallClazzProxy, T>(clazz) {
        });
    }

    @Override
    public  Subscription execute(CallBack callBack) {
        return super.execute(new CallBackProxy, T>(callBack) {
        });
    }
}
自定义PostRequest请求

注:下面代码可以直接拷贝过去使用,其中的TestApiResult修改成自己的ApiResult就可以了

public class CustomPostRequest extends PostRequest {
    public CustomPostRequest(String url) {
        super(url);
    }

    @Override
    public  Observable execute(Type type) {
        return super.execute(new CallClazzProxy, T>(type) {
        });
    }

    @Override
    public  Observable execute(Class clazz) {
        return super.execute(new CallClazzProxy, T>(clazz) {
        });
    }

    @Override
    public  Subscription execute(CallBack callBack) {
        return super.execute(new CallBackProxy, T>(callBack) {
        });
    }
}
新建请求的管理类方便使用
public class HttpManager {
    /**
     * get请求
     */
    public static GetRequest get(String url) {
        return new CustomGetRequest(url);
    }

    /**
     * post请求
     */
    public static PostRequest post(String url) {
        return new CustomPostRequest(url);
    }
}
新的网络请求方式
HttpManager.get("http://japi.juhe.cn/joke/content/list.from")
                .params("key", "f5236a9fb8fc75fac0a4d9b8c27a4e90")
                .params("page", "1")
                .params("pagesize", "10")
                .params("sort", "asc")
                .params("time", "1418745237")
                .execute(new ProgressDialogCallBack(mProgressDialog) {//这么实现是不是没有代理了
                    @Override
                    public void onError(ApiException e) {
                        super.onError(e);
                        showToast(e.getMessage());
                    }

                    @Override
                    public void onSuccess(Result result) {
                        if (result != null) showToast(result.toString());
                    }
                });
使用方式对比

具体源码请查看GitHub中提供的Demo:https://github.com/zhou-you/RxEasyHttp 欢迎加入我的圈子

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/13794.html

相关文章

  • 5分钟教你学会Django系统错误监控

    摘要:一监控所有的请求如何实现系统监控,自动发送错误日志的邮件呢只需配置配置文件即可。设置发送邮件配置信息邮件会发送到设定的邮件列表中。 showImg(https://segmentfault.com/img/remote/1460000015327475); 一、监控所有的request请求 如何实现系统监控,自动发送错误日志的邮件呢? 只需配置配置settings文件即可。 1.设置发...

    Aldous 评论0 收藏0
  • RxEasyHttp一款基于RxJava2+Retrofit2实现简单易用的网络请求框架

    摘要:注和是当下非常火爆的开源框架,均来自神一般的公司。特点比使用更简单更易用。默认初始化如果使用默认始化后,一切采用默认设置。为单个请求设置超时,比如涉及到文件的需要设置读写等待时间多一点。 github源码地址:https://github.com/zhou-you/RxEasyHttp RxEasyHttp 本库是一款基于RxJava2+Retrofit2实现简单易用的网络请求框架,结...

    MadPecker 评论0 收藏0
  • 「码个蛋」2017年200篇精选干货集合

    摘要:让你收获满满码个蛋从年月日推送第篇文章一年过去了已累积推文近篇文章,本文为年度精选,共计篇,按照类别整理便于读者主题阅读。本篇文章是今年的最后一篇技术文章,为了让大家在家也能好好学习,特此花了几个小时整理了这些文章。 showImg(https://segmentfault.com/img/remote/1460000013241596); 让你收获满满! 码个蛋从2017年02月20...

    wangtdgoodluck 评论0 收藏0
  • 网络库与Rxjava2结合常见使用场景介绍

    摘要:本文主要是讲与怎么结合的,也不会的操作符深入讲解,不然就脱离了本文的重心废话不多说了,一起来看看是如何使用的。延迟请求利用的操作符。 前言 之前在github开源过一个网络库RxEasyHttp,这是一款基于RxJava2+Retrofit2实现简单易用的网络请求框架。在这里对网络库的用法就不做过多介绍,感兴趣的可以去了解下。在使用过程中一些网友反馈不知道怎么结合Rxjava2来实现一...

    coolpail 评论0 收藏0
  • 网络库与Rxjava2结合常见使用场景介绍

    摘要:本文主要是讲与怎么结合的,也不会的操作符深入讲解,不然就脱离了本文的重心废话不多说了,一起来看看是如何使用的。延迟请求利用的操作符。 前言 之前在github开源过一个网络库RxEasyHttp,这是一款基于RxJava2+Retrofit2实现简单易用的网络请求框架。在这里对网络库的用法就不做过多介绍,感兴趣的可以去了解下。在使用过程中一些网友反馈不知道怎么结合Rxjava2来实现一...

    BDEEFE 评论0 收藏0

发表评论

0条评论

Charles

|高级讲师

TA的文章

阅读更多
最新活动
阅读需要支付1元查看
<