如何使用retrofit,rxjava和dagger为错误创建通用响应处理程序并验证响应

时间:2017-12-05 06:46:36

标签: android kotlin retrofit2 dagger-2 rx-java2

我试图创建通用架构来使用复杂的json结构,如下所示:

  

Json 格式

{
"type": "success",
"code": "s-groups-0006",
"description": "Index List successfully",
"result": {
    "asOnDate": 1505457095278,
    "indexList": [
        {
            "change": "22.35",
            "changePercent": "0.27",
            "isDefault": true,
            "isEditable": false
        }
    ]
}

}

  

Dagger 格式

@Singleton
fun provideGson(): Gson =
        GsonBuilder()
                .setLenient()
             //   .registerTypeAdapter(BaseResponse::class.java, RestDeserializer<BaseResponse<T>>())
                .create()
  

休息 Deseralizers

 class RestDeserializer<T> : JsonDeserializer<T> {
@Throws(JsonParseException::class)
override fun deserialize(je: JsonElement, type: Type, jdc: JsonDeserializationContext): T? {
    val content = je.asJsonObject

    // Deserialize it. You use a new instance of Gson to avoid infinite recursion
    // to this deserializer
    return Gson().fromJson<T>(content, type)

}

}

  

错误回调

abstract class ErrorCallBack<T : BaseResponse<T>> : DisposableObserver<T>() {

protected abstract fun onSuccess(t: T)

override fun onNext(t: T) {
    //You can return StatusCodes of different cases from your API and handle it here. I usually include these cases on BaseResponse and iherit it from every Response
    onSuccess(t)
}

override fun onError(e: Throwable) {

    when (e) {
        is HttpException -> {
            val responseBody = (e).response().errorBody()
            responseBody?.let {
                L.e("Error in call htttp exception")
            }
        }
        is SocketTimeoutException -> {
            // todo
            L.e("Error in Socket time out")
        }
        is IOException -> {
            // todo
            L.e("Error in IO Exception")
        }
        else -> {
            e.message?.let {
                // todo
            }
        }
    }
}

override fun onComplete() {

}

private fun getErrorMessage(responseBody: ResponseBody): String {
    return try {
        val jsonObject = JSONObject(responseBody.string())
        jsonObject.getString("message")
    } catch (e: Exception) {
        e.message!!
    }

}

}

  

存储库

    override fun getValidateUser(validateUser: ValidateUser): LiveData<ValidateUserResponse> {

    val mutableLiveData = MutableLiveData<ValidateUserResponse>()
    remoteServices.requestValidateUser(validateUser)
            .subscribeOn(Schedulers.io())
            .observeOn(AndroidSchedulers.mainThread())
            .subscribeWith(object : ErrorCallBack<BaseResponse<ValidateUserResponse>>() {
                override fun onSuccess(t: BaseResponse<ValidateUserResponse>) {
                    if (t.type == CommonContents.SUCCESS) {
                        L.d("Success in validate user")
                        mutableLiveData.value = transform(t)
                    } else {
                        L.e("Validate User Error")
                    }
                }
            })
    return mutableLiveData
}
  

数据

data class BaseResponse<out T>(
    @SerializedName(CommonContents.TYPE) val type: String,
    @SerializedName(CommonContents.CODE) val Code: String,
    @SerializedName(CommonContents.DESCRIPTION) val Description: String,
    @SerializedName(CommonContents.RESULT)val result: T? = null)

这些是我的结构,我尝试创建一个通用结构,但在调用Error回调时遇到问题。

请指导我如何实现这一目标。我可以在通用Response中调用泛型方法吗?

  .subscribeWith(object : ErrorCallBack<BaseResponse<ValidateUserResponse>>() {

1 个答案:

答案 0 :(得分:-1)

实现工作代码指南

这是我使代码工作的指南。它基于Test Driven Development的原则。

  1. 在IDE中设置单元测试环境。就个人而言,我一直在使用JUnit 4和Eclipse,但你可能更喜欢JUnit 5和JetBrains的IDE。
  2. 为您的ErrorCallback类构造函数编写单元测试。让它通过。接下来,为每个方法编写单元测试,以确定它的行为与您期望的一样。
  3. 针对某些不同情况编写测试夹具为PublishSubject<BaseResponse<Integer>>的单元测试:正常数据,正常数据序列,正常数据后跟错误,正常数据后跟完成。
  4. 从那里,添加一些测试,以便您可以测试整个可观察链。