Hoang
Hoang

Reputation: 1047

RxJava How do I convert Single<T> in Rxjava to Call<T> in Retrofit or opposite convert

I have an API service class with a method that returns an Call provided by Retrofit. Recently, Rx2Java introduced the Single so I want to change Call to Single but I don't want to change logic. For example :
class interface testAPI{

@GET
Call<Object> get()
}

And now I'd like to change like below

@GET
Single<Object> get()

Is there anyway to convert Single to Call likes :

Single.fromCall

or

Call.fromSingle

Update

@Moinkhan : Thank you for the reply!
I'd like to describe my problem in detail.

Previous version app is working fine with Rest API and Retrofit

 @GET
 Call<Response> get()

Now, we're planing to use GraphQL + Apollo client Android. Apollo client is compatible with Rxjava. The API will be look like below :

class apolloApi {

  fun get(): Single<Response> {
   // Run query code with Apollo Query and Rx2Java
  }
}

If we do that way, we have to change all of previous logic. It takes our effort. ( Definitely, we must do in the future ! )
But now, if we can convert Single to Call, it will be fine ! For example :

class apolloApi {

  private fun get(): Single<Response> {
   // Run query code with Apollo Query and Rx2Java
  }

  fun convertCall(): Call<Response> {
    return get().toCall() // Something like that
  }
}

Upvotes: 2

Views: 1155

Answers (2)

Janos Breuer
Janos Breuer

Reputation: 480

In the Apollo Android docs, there's an example that does not use RxJava, and one that does use it. The one that does not has an API very similar to that of Retrofit Call. It has an enqueue method with a callback with onSuccess and onFailure.

I think a good compromise in your situation would be to start using.the Apollo client without RxJava so that your client code (i.e. the code that currently depends on and calls the Call interface) does not have to be changed.

Later, when you have the resources for the migration, you can migrate it gradually to the RxJava version, using the Rx2Apollo wrapper.

Upvotes: 0

Moinkhan
Moinkhan

Reputation: 12932

Yes you can.. You just need to add below dependency..

implementation 'com.squareup.retrofit2:adapter-rxjava2:2.4.0'

In your retrofit client..

retrofit = Retrofit.Builder()
        .client(client)
        .baseUrl(baseUrl)
        .addCallAdapterFactory(RxJava2CallAdapterFactory.create()) // this line is important
        .addConverterFactory(GsonConverterFactory.create())
        .build()

for conversion from Call > Single or Signle > Call you can create extension function in kotlin.

from Call to Single

fun <T> Call<T>.toSingle(): Single<Response<T>> {
    val single = SingleSubject.create<Response<T>>()
    this.enqueue(object : Callback<T> {
        override fun onFailure(call: Call<T>, t: Throwable) {
            single.onError(t)
        }

        override fun onResponse(call: Call<T>, response: Response<T>) {
            single.onSuccess(response)
        }
    })

    return single
}

Upvotes: 2

Related Questions