Rxjava2 doFinally

430 阅读1分钟

doFinally 在最后执行,finally的意思是总是会执行,调用onError 或者onComplete或者dispose,都会执行。

Observable.create(new ObservableOnSubscribe<String>() {
            @Override
            public void subscribe(@NotNull ObservableEmitter<String> emitter) throws Exception {
                emitter.onNext("1");
                mDisposable.dispose();
            }
        }).doFinally(new Action() {
            @Override
            public void run() throws Exception {
                System.out.println("doFinally");
            }
        }).subscribe(new Observer<String>() {
            @Override
            public void onSubscribe(@NotNull Disposable d) {
                System.out.println("onSubscribe");
                mDisposable = d;
            }

            @Override
            public void onNext(@NotNull String s) {
                System.out.println("onNext " + s);
            }

            @Override
            public void onError(@NotNull Throwable e) {
                System.out.println("onError");
            }

            @Override
            public void onComplete() {
                System.out.println("onComplete");
            }
        });

输出

onSubscribe
onNext 1
doFinally

看源码

  public final Observable<T> doFinally(Action onFinally) {
        ...
        return RxJavaPlugins.onAssembly(new ObservableDoFinally<T>(this, onFinally));
    }

ObservableDoFinally类中,不论执行到哪个方法,都会执行 runFinally()

 public void onError(Throwable t) {
            downstream.onError(t);
            runFinally();
        }

        @Override
        public void onComplete() {
            downstream.onComplete();
            runFinally();
        }

        @Override
        public void dispose() {
            upstream.dispose();
            runFinally();
        }

compareAndSet(0, 1)原子控制runFinally只会执行一次。

 void runFinally() {
   
            if (compareAndSet(0, 1)) {
                try {
                    onFinally.run();
                } catch (Throwable ex) {
                    Exceptions.throwIfFatal(ex);
                    RxJavaPlugins.onError(ex);
                }
            }
        }