Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Observable.just vs Single in RxJava

I'm new to RxJava and RxAndroid and trying to understand the difference between Observable.just and Single. It looks like each is designed to emit one item for its observer.

Here is the code of my simple Android activity with two buttons. The first button creates an Observable, and the second button creates a Single:

findViewById(R.id.just).setOnClickListener(view -> Observable.just("item").subscribe(
        new Observer<String>() {
            @Override
            public void onSubscribe(Disposable d) {
                Log.d(LOG_TAG, "just onSubscribe");
            }

            @Override
            public void onNext(String s) {
                Log.d(LOG_TAG, "just s=" + s);
            }

            @Override
            public void onError(Throwable e) {
                Log.e(LOG_TAG, "just e=" + e);
            }

            @Override
            public void onComplete() {
                Log.d(LOG_TAG, "just onComplete");
            }
        }));

findViewById(R.id.single).setOnClickListener(
        view -> Single.create((SingleOnSubscribe<String>) e -> {
        })
                .subscribe(new SingleObserver<String>() {
                    @Override
                    public void onSubscribe(Disposable d) {
                        Log.d(LOG_TAG, "single onSubscribe");
                    }

                    @Override
                    public void onSuccess(String o) {
                        Log.d(LOG_TAG, "single onSuccess");
                    }

                    @Override
                    public void onError(Throwable e) {
                        Log.d(LOG_TAG, "single onError", e);
                    }
                }));

When I press the "Just" button, onSubscribe, onNext, and onComplete are called.

When I press the "Single" button, only SingleObserver#onSubscibe is called, and SingleObserver#onSuccess is not.

The versions of RxJava and RxAndroid in my build.gradle:

compile 'io.reactivex.rxjava2:rxandroid:2.0.1'
// Because RxAndroid releases are few and far between, it is recommended you also
// explicitly depend on RxJava's latest version for bug fixes and new features.
compile 'io.reactivex.rxjava2:rxjava:2.1.3'
like image 845
Maksim Dmitriev Avatar asked Oct 12 '17 05:10

Maksim Dmitriev


People also ask

What is single observable in RxJava?

This article is part of RxJava Introduction series. You can checkout the entire series here: Single is an Observable that always emit only one value or throws an error. A typical use case of Single observable would be when we make a network call in Android and receive a response.

How to convert observable to single in Java?

Just call single.toObservable () and you’re good. But transforming Observable to Single is not that simple: if it happens that Observable emits exactly one value and completes (or terminates with error without emitting values) then it is pretty straightforward, otherwise one need to set up some additional rules.

What is the use case of single observable in Android?

A typical use case of Single observable would be when we make a network call in Android and receive a response. Sample Implementation: The below code always emits a Single user object. We use a Single Observable and a Single Observer. The Single Observer always emits only once so there is no onNext () .

What is the difference between single Maybe and completable observables?

We’ll be looking into Single, Maybe and Completable in brief. Single, Maybe and Completable are one or no emission of items. Single is an Observable which only emits one item or throws an error. Single emits only one value and applying some of the operator makes no sense. Like we don’t want to take value and collect it to a list.


1 Answers

Your code is working as expected. With the first you emit item but not in the second.

You need to change to

 findViewById(R.id.single).setOnClickListener(
    view -> Single.create((SingleOnSubscribe<String>) e -> {
            if(!e.isDisposed())
            e.onSuccess("item");
    })
            .subscribe(new SingleObserver<String>() {
                @Override
                public void onSubscribe(Disposable d) {
                    Log.d(LOG_TAG, "single onSubscribe");
                }

                @Override
                public void onSuccess(String o) {
                    Log.d(LOG_TAG, "single onSuccess" + " "+o);
                }

                @Override
                public void onError(Throwable e) {
                    Log.d(LOG_TAG, "single onError", e);
                }
            }));

Now you should see "item" in onSuccess.

Say you want to do some operation then return a string you would do as suggested above. Suppose your operation fails you can then do e.onError(new IOException());) , now you should see the error in onError

like image 167
Raghunandan Avatar answered Sep 23 '22 02:09

Raghunandan