Search code examples
javaandroidrx-javarx-java2

Single.fromCallable() - Chaining two calls, one after another


I'm using Single.fromCallable() to make a network call and I want to use the data from the response to make a second call.

How can I chain these two calls instead of nesting them?

private void queryForUser() {
    Single.fromCallable(() -> remoteRepository.queryForUser()))
                .subscribeOn(Schedulers.io())
                .observeOn(AndroidSchedulers.mainThread())
                .subscribe(response-> {

                    String username = response.getUsername();

                    //Perform second call
                    performSecondQuery(username);

                }, err -> {
                    Log.e(TAG, "Failed to get user", err);
               
                });

}
private void performSecondQuery(String username){
        Single.fromCallable(() -> remoteRepository.performSecondQuery(username)))
                .subscribeOn(Schedulers.io())
                .observeOn(AndroidSchedulers.mainThread())
                .subscribe(secondQueryResult -> {

                    Log.d(TAG, "performSecondQuery: " + secondQueryResult);

                }, err -> {
                    Log.e(TAG, "Failed to perform second query", err);
                });
}

Solution

  • My Java lambda syntax is rusty, but using flatMap() should give you something like this:

    private Single<Whatever> performSecondQuery(String username){
            return Single.fromCallable(() -> remoteRepository.performSecondQuery(username)))
    }
    
    private void queryForUser() {
        Single.fromCallable(() -> remoteRepository.queryForUser()))
                    .flatMap { response -> performSecondQuery(response.getUsername()) }
                    .subscribeOn(Schedulers.io())
                    .observeOn(AndroidSchedulers.mainThread())
                    .subscribe(
                       // TODO something with the result
                    }, err -> {
                        Log.e(TAG, "Failed to get user", err);
                    });
    }
    

    (note: I don't know what the second query is doing, so I don't know what Whatever is — it would be the return type of remoteRepository.performSecondQuery())