研发工程师和开发工程师,seo优化方案执行计划,professional wordpress,大连设计网站公司简介 RxHttp是基于OkHttp的二次封装#xff0c;并于RxJava做到无缝衔接#xff0c;一条链就能发送一个完整的请求。主要功能如下#xff1a; 支持Get、Post、Put、Delete等任意请求方式#xff0c;可自定义请求方式支持Json、DOM等任意数据解析方式#xff0c;可自定义数据…
简介 RxHttp是基于OkHttp的二次封装并于RxJava做到无缝衔接一条链就能发送一个完整的请求。主要功能如下 支持Get、Post、Put、Delete等任意请求方式可自定义请求方式支持Json、DOM等任意数据解析方式可自定义数据解析器支持文件下载/上传及进度的监听并且支持断点下载支持在Activity/Fragment的任意生命周期方法自动关闭未完成的请求支持添加公共参数/头部信息且可动态更改baseUrl支持请求串行和并行gradle依赖 implementation com.rxjava.rxhttp:rxhttp:1.0.4
//注解处理器生成RxHttp类即可一条链发送请求
annotationProcessor com.rxjava.rxhttp:rxhttp-compiler:1.0.4
//管理RxJava及生命周期Activity/Fragment 销毁自动关闭未完成的请求
implementation com.rxjava.rxlife:rxlife:1.0.4RxHttp 源码RxLife 源码 初始化 //设置debug模式此模式下有日志打印
HttpSender.setDebug(boolean debug)
//非必须,只能初始化一次第二次将抛出异常
HttpSender.init(OkHttpClient okHttpClient)
//或者调试模式下会有日志输出
HttpSender.init(OkHttpClient okHttpClient, boolean debug)此步骤是非必须的不初始化或者传入null即代表使用默认OkHttpClient对象。 疑问标题不是说好的是RxHttp这么用HttpSender做一些初始化呢这里先卖一个关子后面会解答 添加公共参数/头部及重新设置url 相信大多数开发者在开发中都遇到要为Http请求添加公共参数/请求头甚至要为不同类型的请求添加不同的公共参数/请求头为此RxHttp为大家提供了一个静态接口回调如下每发起一次请求此接口就会被回调一次并且此回调在子线程进行(在请求执行线程回调) HttpSender.setOnParamAssembly(new Function() {Overridepublic Param apply(Param p) { if (p instanceof GetRequest) {//根据不同请求添加不同参数} else if (p instanceof PostRequest) {} else if (p instanceof PutRequest) {} else if (p instanceof DeleteRequest) {}//可以通过 p.getSimpleUrl() 拿到url更改后重新设置//p.setUrl();return p.add(versionName, 1.0.0)//添加公共参数.addHeader(deviceType, android); //添加公共请求头}
});然后有些请求我们不希望添加公共参数/请求头RxHttp又改如何实现呢很简单发起请求前设置不添加公共参数如下 Param param Param.get(http://...)//设置是否对Param对象修饰即是否添加公共参数默认为true.setAssemblyEnabled(false); //设为false就不会回调上面的静态接口到这也许你们会有疑问Param 是什么东东下面就为大家讲解。 Param 首先我们来看看如何发送一个请求 Param param Param.get(http://...).add(key, value);
Disposable disposable HttpSender.from(param).subscribe(s - { //这里的s为String类型即Http请求的返回结果//成功回调}, throwable - {//失败回调});疑问说好的一条链发送请求呢别着急还没到放大招的时候 到这我可以告诉大家Param承担的是一个请求体的一个角色我们通过Param可以确定请求方式(如Get、Post、Put、Delete等请求方式)、添加请求参数、添加请求头、添加File对象等然后通过HttpSender传入Param对象将请求发送出去。 HttpSender 到这有人又有疑问前面初始化、设置公共参数都用到了HttpSender这里发送请求又用到了HttpSender ,那么它又是承担怎么样的一个角色呢看名字我们可以理解为它就是一个请求发送者通过一个from操作符传入一个Param对象然后返回一个RxJava的Observable对象此时我们就可以使用RxJava强大的操作符去处理相关的逻辑(这就是简介说的做到了与RxJava的无缝链接)在这我们只是使用了subscribe操作符去订阅观察者。 RxHttp 现在我们正式放大招标题说好的一条链发送请求既然吹牛了就要去实现它。拿上面的例子看看我们如何一条链实现上代码 RxHttp.get(http://...).add(key, value).from() .subscribe(s - { //这里的s为String类型即Http请求的返回结果//成功回调}, throwable - {//失败回调});我们的主角RxHttp终于登场了可以看到使用RxHttp类我们就实现了一条链完成请求的发送那它又是承担一个什么角色呢我们暂时可以理解为RxHttpParamHttpSender并且还有自己特殊的使命。至于什么使用后面会讲解。 我们现在来解疑惑为什么我们的库叫RxHttp但是初始化、设置公共参数等却用HttpSender因为RxHttp这个类不在RxHttp库中它是通过注解处理器生成的类。前面我们看到gradle依赖时使用了 annotationProcessor com.rxjava.rxhttp:rxhttp-compiler:1.0.2该注解处理器的目的就是在项目中生成RxHttp类那为何不直接把它写到库里面去呢前面讲过因为它有自己的使命而这个使命就是我们可以通过注解在RxHttp中生成自定义的api我们来看看如何使用注解。 动态设置baseUrl 现实开发中大部人开发者都会将baseUrl 单独抽取出来RxHttp也考虑到了这一点RxHttp通过DefaultDomain注解来配置baseUrl看代码 public class Url {DefaultDomain() //设置为默认域名public static String baseUrl http://ip.taobao.com/;
}rebuild一下项目此时我们发送请求就可以直接传入path路径如下 RxHttp.get(/service/getIpInfo.php).add(key, value).from() .subscribe(s - { //这里的s为String类型即Http请求的返回结果//成功回调}, throwable - {//失败回调});RxHttp在发送请求前会对url做判断如果没有域名就会自定加上默认的域名也就是baseUrl。然后如果我们不想使用默认的域名呢RxHttp也考虑到来提供了一个Domain注解我们再来看看用法 public class Url {Domain(name Update9158) //设置非默认域名name 可不传不传默认为变量的名称public static String update http://update.9158.com;DefaultDomain() //设置为默认域名public static String baseUrl http://ip.taobao.com/;
}此时再rebuild一下项目就会在RxHttp类中生成一个setDomainToUpdate9158IfAbsent()方法其中的Update9158字符就是name指定的名字然后发请求就可以这样 RxHttp.get(/service/getIpInfo.php).setDomainToUpdate9158IfAbsent().add(key, value).from() .subscribe(s - { //这里的s为String类型即Http请求的返回结果//成功回调}, throwable - {//失败回调});此时RxHttp检测到url已经配置了域名就不会再去使用默认的域名。同样的setDomainToUpdate9158IfAbsent也会检测url 有没有配置域名如果配置了也不会使用我们指定的域名。 注意Domain注解可以在多个地方使用而DefaultDomain()只能在一个地方使用否则编译不通过很好理解默认域名只可能有一个。两个注解都要使用在public static修饰的String类型变量上对final关键字没有要求可写可不写这就表明baseUrl 可以动态更改RxHttp始终会拿到的最新的baseUrl 。怎么样是不是很nice!! 更多注解使用请查看RxHttp 扩展篇之注解处理器 Generated API八 接下来我们来看看如何发送Post请求、如何在Activity/Fragment销毁时自动关闭为完成的请求、如何上传/下载文件及进度的监听、如何把Http返回的结果自动解析成我们想要的对象。 注以下讲解均使用RxHttp Post RxHttp.postForm(http://...).add(key, value).from() .subscribe(s - { //这里的s为String类型即Http请求的返回结果//成功回调}, throwable - {//失败回调});可以看到跟上面的Get请求只有一点不同Get是RxHttp.get而Post是RxHttp.postForm除此之外没有任何区别我们在看来来RxHttp都有哪些静态方法供我们选择请求方式可以看到默认提供了10个静态方法供我们选择具体的请求方式有Get、Post、Put等而Post等又分为postForm和postJson这个好理解前者是发送表单形式的post请求后者是发送json字符串的post请求。 现实中这些默认的请求方式显然不能满足我们的需求如我要发送加密的post请求这个时候该怎么办呢此时就需要我们自定义请求方式。自定义请求方式请查看RxHttp 扩展篇之Param扩展七 Activity 销毁自动关闭未完成的请求 上面的案例中在Activity/Fragment销毁时如果请求还未完成就会造成Activity/Fragment 无法回收导致内存泄漏。这是非常严重的问题那么RxHttp是如何解决的呢此时就要引入我自己写的另一个库RxLife直接看看如何使用 RxHttp.postForm(http://...).add(key, value).from().as(RxLife.as(this)) //订阅观察者前加上这句话即可.subscribe(s - {//成功回调}, throwable - {//失败回调});//或者RxHttp.postForm(http://...).add(key, value).from().as(RxLife.asOnMain(this)) //asOnMain 可以在主线程回调观察者.subscribe(s - {//成功回调}, throwable - {//失败回调});这里的this为LifecycleOwner对象它是一个接口这里我们传入的是Activity因为Activity实现了LifecycleOwner接口。当Activity/Fragment销毁时会将RxJava的管道中断管道中断时又会将未完成的请求自动关闭。 对RxLife不了解的同学请查看Android RxLife 一款轻量级别的RxJava生命周期管理库 (一)这里不详细讲解。在下面的讲解中我们均会使用RxLife 文件上传/下载及进度监听 使用RxHttp可以很优雅的实现文件上传/下载及进度的监听如何优雅直接上代码 文件上传 RxHttp.postForm(http://...) //发送Form表单形式的Post请求.add(key, value).add(file1, new File(xxx/1.png)) //添加file对象.add(file2, new File(xxx/2.png)).from() //from操作符是异步操作.as(RxLife.asOnMain(this)) //感知生命周期并在主线程回调.subscribe(s - { //成功回调}, throwable - {//失败回调});可以看到文件上传跟普通的post请求其实没啥区别无非就是在post请求的基础上调用add方法添加要上传的文件对象。 文件下载 //文件存储路径String destPath getExternalCacheDir() / System.currentTimeMillis() .apk;RxHttp.get(http://update.9158.com/miaolive/Miaolive.apk).download(destPath) //注意这里使用download操作符并传入本地路径.as(RxLife.asOnMain(this)) //感知生命周期并在主线程回调.subscribe(s - {//下载成功,回调文件下载路径}, throwable - {//下载失败});下载跟普通请求不同的是下载使用的是download操作符其它都一样。 文件下载进度监听 //文件存储路径String destPath getExternalCacheDir() / System.currentTimeMillis() .apk;RxHttp.get(http://update.9158.com/miaolive/Miaolive.apk).downloadProgress(destPath) //注:如果需要监听下载进度使用downloadProgress操作符.observeOn(AndroidSchedulers.mainThread()).doOnNext(progress - {//下载进度回调,0-100仅在进度有更新时才会回调最多回调101次最后一次回调文件存储路径int currentProgress progress.getProgress(); //当前进度 0-100long currentSize progress.getCurrentSize(); //当前已下载的字节大小long totalSize progress.getTotalSize(); //要下载的总字节大小String filePath progress.getResult(); //文件存储路径最后一次回调才有内容}).filter(Progress::isCompleted)//下载完成才继续往下走.map(Progress::getResult) //到这说明下载完成返回下载目标路径.as(RxLife.as(this)) //感知生命周期.subscribe(s - {//s为String类型这里为文件存储路径//下载完成处理相关逻辑}, throwable - {//下载失败处理相关逻辑});下载进度的监听我们稍微看一下 首先一点下载使用download操作符而下载进度监听使用downloadProgress操作符随后我们使用了doOnNext操作符处理进度回调注意这里是仅当有进度更新时才会回调其中的progress变量是一个Progress类型的对象我们贴上源码 public class ProgressT {private int progress; //当前进度 0-100private long currentSize;//当前已完成的字节大小private long totalSize; //总字节大小private T mResult; //http返回结果,上传/下载完成时调用//省略get/set方法
}由于进度回调会执行101次(上面注释有解释)而最下面观察者其实是不需要关心这么多事件的只需要关心最后下载完成的事件所以使用了filter操作符过滤事件只要还未下载完成就将事件过滤调不让往下走。最终下载完成后拿到本地下载路径。 文件上传进度监听 RxHttp.postForm(http://www.......) //发送Form表单形式的Post请求.add(file1, new File(xxx/1.png)).add(file2, new File(xxx/2.png)).add(key1, value1)//添加参数非必须.add(key2, value2)//添加参数非必须.addHeader(versionCode, 100) //添加请求头,非必须.uploadProgress() //注:如果需要监听上传进度使用uploadProgress操作符.observeOn(AndroidSchedulers.mainThread()) //主线程回调.doOnNext(progress - {//上传进度回调,0-100仅在进度有更新时才会回调,最多回调101次最后一次回调Http执行结果int currentProgress progress.getProgress(); //当前进度 0-100long currentSize progress.getCurrentSize(); //当前已上传的字节大小long totalSize progress.getTotalSize(); //要上传的总字节大小String result progress.getResult(); //Http执行结果最后一次回调才有内容}).filter(Progress::isCompleted)//过滤事件上传完成才继续往下走.map(Progress::getResult) //到这说明上传完成拿到Http返回结果并继续往下走.as(RxLife.as(this)) //感知生命周期.subscribe(s - { //s为String类型由SimpleParser类里面的泛型决定的//上传成功处理相关逻辑}, throwable - {//上传失败处理相关逻辑});上传进度监听使用downloadProgress操作符剩下的操作跟下载进度监听的操作都一样通过doOnNext监听上传进度然后过滤事件最终拿到Http的返回结果。 数据解析器Parser 在上面的案例中观察者拿到数据类型都是String类型然后现实开发中我们经常需要对数据解析成我们想要的对象RxHttp考虑到了这一点现在我们就来看看如何的到我们想要的对象 我们拿淘宝获取IP的接口作为测试接口http://ip.taobao.com/service/getIpInfo.php?ip63.223.108.42 对应的数据结构如下 public class Response {private int code;private Address data;//省略set、get方法class Address {//为简单起见省略了部分字段private String country; //国家private String region; //地区private String city; //城市//省略set、get方法}
}开始发送请求 RxHttp.get(http://ip.taobao.com/service/getIpInfo.php) //Get请求.add(ip, 63.223.108.42)//添加参数.addHeader(accept, */*) //添加请求头.addHeader(connection, Keep-Alive).addHeader(user-agent, Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1;SV1)).fromSimpleParser(Response.class) //这里返回ObservableResponse 对象.as(RxLife.asOnMain(this)) //感知生命周期并在主线程回调.subscribe(response - {//成功回调}, throwable - {//失败回调});可以看到这里我们没有用from操作符而是用了fromSimpleParser操作符并且传入Response.class最后观察者拿到的response变量就是Response类型的对象。怎么样是不是很简单。RxHttp为我们提供了一系列的fromXXX方法我们来看一下: 我们可以看到一些基本类型的封装对象RxHttp都为我们封装好了还有一个fromListParser方法此方法是用来解析集合对象的一些常见的数据结构RxHttp都为我们考虑到了并封装好了然后一些不常见的数据呢眼尖的你也许发现了上图中还有一个T ObservableT from(ParserT parser)方法它允许我们传入一个自定义的解析器更多解析器的介绍请查看RxHttp 之强大的数据解析功能二 最后附上RxHttp一些常用的用法如下 RxHttp.postForm(/service/getIpInfo.php) //发送Form表单形式的Post请求.setDomainToUpdate9158IfAbsent() //手动设置域名此方法是通过Domain注解生成的.tag(RxHttp.get) //为单个请求设置tag.setUrl(http://...) //重新设置url.setAssemblyEnabled(false) //设置是否添加公共参数默认为true.cacheControl(CacheControl.FORCE_NETWORK) //缓存控制.setParam(Param.postForm(http://...)) //重新设置一个Param对象.add(new HashMap()) //通过Map添加参数.add(int, 1) //添加int类型参数.add(float, 1.28838F) //添加float类型参数.add(double, 1.28838) //添加double类型参数.add(key1, value1) //添加String类型参数.add(key2, value2, false) //根据最后的boolean字段判断是否添加参数 .add(file1, new File(xxx/1.png)) //添加文件对象.addHeader(headerKey1, headerValue1) //添加头部信息.addHeader(headerKey2, headerValue2, false)//根据最后的boolean字段判断是否添加头部信息 .fromSimpleParser(String.class) //这里返回ObservableT 对象 fromXXX都是异步操作符//感知生命周期并在主线程回调当Activity/Fragment销毁时自动关闭未完成的请求.as(RxLife.asOnMain(this)) .subscribe(s - { //订阅观察者//成功回调}, throwable - {//失败回调});小结 到这RxHttp的基本用法我们就讲解完毕了可以看到使用RxHttp类一条链就能完成一个完整的Http请求简单一点就是请求三部曲 首先确定请求方式并添加相关参数然后确定解析器指定要解析成的类型最后订阅观察者开始发送请求以上所有的案例都离不开这3个步骤。最后你会发现RxHttp除了提供的一系列强大的功能外在写法上不管什么请求都极其的相似只要通过RxHttp类就能一条链完成所有的请求极大的降低了学习成本。 注:要想在项目中生成RxHttp类至少需要使用一次注解类否则检测不到注解就无法生成。 如果你觉得RxHttpRxLife好用请记得给我star 如果有好的idea请留言或者联系我。 更过详情请查看RxHttp系列其它文章 RxHttp 之强大的数据解析功能二 RxHttp 介绍篇之Param介绍三 RxHttp 介绍篇之多请求串行与并行四 RxHttp 扩展篇之Param扩展六 RxHttp 扩展篇之注解处理器 Generated API七 --------------------- 作者刘敬兴 来源CSDN 原文https://blog.csdn.net/liujingxing93/article/details/86600477 版权声明本文为作者原创文章转载请附上博文链接