1
votes
  1. API class using Retrofit

    class interface TestApi {
      @GET("/path/abc/xyz") 
      fun get(): Single
    }
    
  2. UseCase class

    fun getResult(): Single {
          return testApi.get()
            .map{ response -> 
                val type = response.type
                when(type){
                 null -> throw Exception()
                 else -> response
                } 
             }
            .retryWhen{ throwableHandler ->
                throwableHandler.flatMap {
                    when(it) {
                       is Exception() -> Flowable.error(it)
                       else -> Flowable.timer(3,TimeUnit.SECONDS)
                     }
                }
            }
            .timeout(60, TimeUnit.SECONDS)
        }
        
  3. MainClass.kt

    usecase.getResult()
            .subscribeOn(Schedulers.io())
            .observeOn(AndroidSchedulers.mainThread())
            .subscribeBy(onError = {Log.d(TAG,"Error")},
                         onSuccess = {Log.d(TAG,"Next")})
    
  4. When app run :
    If api return NULL, retryWhen() will be invoked then api is called again. Event not timeout reached and api return Not NUL result -> onSuccess is called. This is correctly processing of retryWhen() operator in rxJava.

My Problem:
If I write some test method (to pretend API Retrofit) in MainClass.kt looks like below:

private fun testPretend(): Single<Animal> {
  return Single.just(Animal)
}

MainClass.kt looks like:

testPretend()
    .subscribeOn(Schedulers.io())
    .observeOn(AndroidSchedulers.mainThread())
    .subscribeBy(onError = {Log.d(TAG,"Error")},
                     onSuccess = {Log.d(TAG,"Next")})

So event retryWhen is invoked , testPretend() method is not called again. What is the problem here?
And what is difference between Single return by testPrerend() and Retrofit API ?

1
fun get() : Single<Animal>Bulma
fun getResult(): Single<Animal>Bulma
Sorry I can not format the description @@Bulma

1 Answers

1
votes

The method testPretend() is not called again because the observable that it returned is what is being resubscribed to. If you want the method to be invoked again upon resubscription, you will need to do something like this:

Single.defer( () => testPretend() )
  ...
  .retryWhen( ... )
  ...;

This will invoke testPretend() upon resubscription.