Ali
Ali

Reputation: 9994

Convert two RxJava requests to one request

I have two requests that I execute using RxJava. They should run one after the other. This is what I have at the current moment :

   fun showPhotos() {
            _liveData.postValue(Resource.Loading())
            compositeDisposable.add(useCase.getPhotos()
                .subscribe({
                    showPosts(it)
                }) {
                    _liveData.postValue(Resource.Failure(it.localizedMessage))
                    Timber.e(it)
                })
        }


    private fun showPosts(networkPhotos: List<NetworkPhoto>) {
        compositeDisposable.add(useCase.getPost()
            .subscribe({ networkPosts ->
                _liveData.postValue(
                    Resource.Success(PostAndImages(networkPosts, networkPhotos).asDomaineModel())
                )
            }) {
                _liveData.postValue(Resource.Failure(it.localizedMessage))
                Timber.e(it)
            })
    }

Is there any solution that I can make one RxJava call instead of executing two requests sequentially ?

Upvotes: 1

Views: 82

Answers (3)

Sergei Buvaka
Sergei Buvaka

Reputation: 611

If you need to run 2 queries sequentially, you can use the flatMap operator.

data class RequestWrapper(var photos: YourType? = null, var networkPosts : YourType? = null)

fun sequentiallyRequest(){
    val requestWrapper = RequestWrapper()

useCase.getPhotos()
    .map{requestWrapper.photos= it}
    .flatMap{useCase.getPost()}
    .map{requestWrapper.networkPosts = it}
    .subscribe({
         _liveData.postValue(
                Resource.Success(PostAndImages(requestWrapper.networkPosts, networkPhotos).asDomaineModel())
            )
})

Or, use operator zip. But in this case, the requests will be executed in parallel.

Single.zip(
     useCase.getPhotos(),
     useCase.getPost(),
     Pair::new)
     .subscribe(pair -> {
         showPosts(pair.first)
         _liveData.postValue(
                Resource.Success(PostAndImages(pair.second, networkPhotos).asDomaineModel())
}

Upvotes: 1

Resul Bal
Resul Bal

Reputation: 1

You may using zip. Queries will work in order.

Single.Zip(
  useCase.getPhotos().subscribeOn(Schedulers.newThread()),
  useCase.getPost().subscribeOn(Schedulers.newThread()),
  BiFunction { photos: ????, posts: ???? -> Pair(photos, posts) }
)
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe({
  it.first is photos
  it.second is posts
},{
  error
})

Upvotes: 0

Antonis Radz
Antonis Radz

Reputation: 3097

You can use .flatMap() if one depends on another or .zip() if you just need to run them both at once and merge them after both completed

Upvotes: 0

Related Questions