Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

RXJava combining multiple subscriptions

So I have a situation I cannot seem to solve at all.

I have a situation where I want to run two network requests in parallel and then run some code at the end of each network request then at the end of the processing of each network request run additional.

Modeled like this

GET -> /users (run unique code to this request independently once the request is done)
GET -> /groups (run some unique code to this request independently once the request is done)
Both requests are done, now run some unique code independent of the request processing.

I've been trying to do a Observable.merge but that seems hopefully, as it won't allow me to keep the subscription code separate from one massive handler. Does anyone have a suggestion?

like image 668
adrian Avatar asked Jul 31 '26 08:07

adrian


1 Answers


One of a options is to use map for doing extra work on each response and then zip to join results; see example:

    //this emulates the first network call
    Observable<List<String>> o1 = Observable.just(Arrays.asList("user1", "user2"));
    //when the data arrives, you may transform it 
    Observable<List<String>> m1 = o1.map(new Func1<List<String>, List<String>>() {
        @Override
        public List<String> call(List<String> users) {
            return users;
        }
    });

    //and the same for the second network call
    Observable<List<String>> o2 = Observable.just(Arrays.asList("group1", "group2"));
    Observable<List<String>> m2 = o2.map(new Func1<List<String>, List<String>>() {
        @Override
        public List<String> call(List<String> groups) {
            return groups;
        }
    });

    //when both network calls succeed you can merge results using zip method    
    Observable<Map<String, List<String>>> result =  Observable.zip(m1, m2, new Func2<List<String>, List<String>, Map<String, List<String>>>() {
        @Override
        public Map<String, List<String>> call(List<String> users, List<String> groups) {
            Map<String, List<String>> result = new HashMap<String, List<String>>();
            for(String user: users){
                result.put(user, groups);
            }
            return result;
        }
    });
    /// now you can return the result


    /// finally you have to subscibe to get the results, e.g:
    result.subscribe(new Action1<Map<String, List<String>>>() {
        @Override
        public void call(Map<String, List<String>> stringListMap) {
            for(String user: stringListMap.keySet()){
                System.out.println("User :"+user+", groups :"+stringListMap.get(user));
            }
        }
    });
like image 51
Marek Hawrylczak Avatar answered Aug 01 '26 21:08

Marek Hawrylczak



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!