以前的文章 RxJava处理业务异常的几种方式 曾经介绍过 Retrofit 的异常能够有多种处理方式。react
其中,可使用 RxJava 的错误处理操做符,它们是专门用来处理异常的。bash
随便例举两个操做符:网络
onErrorReturn 操做符,表示当发生错误的时候,发射一个默认值而后结束数据流。因此 Subscriber 看不到异常信息,看到的是正常的数据流结束状态。并发
onErrorResumeNext 操做符,表示当错误发生的时候,使用另一个数据流继续发射数据。在返回的被观察者中是看不到错误信息的。函数
此次我结合 Kotlin 扩展函数的特性来尝试处理异常。post
网络请求返回的 Response 大可能是采用以下这种形式:ui
{
"code":0,
"message":"success",
"data":{
...
}
}
复制代码
对于客户端开发而言,咱们会封装一个基类的HttpResponse。this
data class HttpResponse<T>(
var code: Int = -1, //0: 成功 1: xxx错误或过时 2: 业务逻辑错误 500:系统内部错误 998表示Token无效
var message: String? = null,
var data: T? = null
) : UnProguard {
val isOkStatus: Boolean
get() = code == 0
}
复制代码
其中,UnProguard是一个空的接口,主要是方便 App 在混淆的时候保留部分类。spa
interface UnProguard : Serializable
复制代码
一般状况下,咱们会在 Observer 的 onError 中按照以下的方式处理异常:code
viewModel.getHelps(this)
.subscribe({
if (it.isOkStatus) {
multi_status_view.showContent()
adapter.addData(it.data?.list)
} else {
multi_status_view.showError()
}
}, { multi_status_view.showError() })
复制代码
若是咱们利用 RxJava 的错误处理操做符,能够编写以下的扩展函数:
import com.safframework.utils.RetryWithDelay
import io.reactivex.Maybe
/** * * @FileName: * cn.magicwindow.core.ext.`Maybe+Extension`.kt * @author: Tony Shen * @date: 2018-07-19 17:31 * @version V1.0 <描述当前版本功能> */
/** * 尝试重试 * 默认有3次重试机会,每次的延迟时间是1000ms */
fun <T> Maybe<T>.retryWithDelayMillis(maxRetries: Int=3, retryDelayMillis: Int=1000): Maybe<T> =
this.retryWhen(RetryWithDelay(maxRetries,retryDelayMillis))
/** * 遇到错误时,可以提早捕获异常,并发射一个默认的值。 * 后面无须再作异常处理 */
fun <T> Maybe<T>.errorReturn(defValue:T): Maybe<T> = this.onErrorReturn {
it -> it.printStackTrace()
return@onErrorReturn defValue
}
fun <T> Maybe<T>.errorReturn(defValue:T,action: (Throwable) -> Unit): Maybe<T> = this.onErrorReturn {
action.invoke(it)
return@onErrorReturn defValue
}
/** * 遇到错误时,可以提早捕获异常,并返回一个新的Maybe * 后面无须再作异常处理 */
fun <T> Maybe<T>.errorResumeNext(defValue:T):Maybe<T> = this.onErrorResumeNext(Maybe.just(defValue))
fun <T> Maybe<T>.errorResumeNext():Maybe<T> = this.onErrorResumeNext(Maybe.empty())
复制代码
扩展函数 errorReturn 的使用:
viewModel.getHelps(this)
.errorReturn(HttpResponse()) {
multi_status_view.showError()
}
.subscribe{
if (it.isOkStatus) {
multi_status_view.showContent()
adapter.addData(it.data?.list)
} else {
multi_status_view.showError()
}
}
复制代码
这样无须在 onError 中处理异常,并且 errorReturn 仍是一个高阶函数。它的 action 参数传递的是一个函数,专门用于处理异常。每个网络请求的异常处理并不会都同样,能够用该函数来传递不一样的异常处理。
合理利用 Kotlin 的扩展函数,能够编写优雅的代码。而使用高阶函数,则能够达到的进一步的抽象。
该系列的相关文章:
Java与Android技术栈:每周更新推送原创技术文章,欢迎扫描下方的公众号二维码并关注,期待与您的共同成长和进步。