rxjava 2.0 介紹

112
RxJava 2.0 介紹 黃千碩 (Kros) oSolve, Ltd./打趣 Mobile App Developer

Upload: kros-huang

Post on 09-Jan-2017

1.118 views

Category:

Engineering


0 download

TRANSCRIPT

  • RxJava 2.0 (Kros)

    oSolve, Ltd./Mobile App Developer

  • RxJava

    RxJava Android RxJava https://speakerdeck.com/ch8908/rxjava-jie-shao-yu-android-zhong-de-rxjava

    https://speakerdeck.com/ch8908/rxjava-jie-shao-yu-android-zhong-de-rxjavahttps://speakerdeck.com/ch8908/rxjava-jie-shao-yu-android-zhong-de-rxjava

  • 2.0 RxJava 2.0 has been completely rewritten from scratch on top of

    the Reactive-Streams specification. The specification itself has evolved out of RxJava 1.x and provides a common baseline for reactive systems and libraries.

    Reactive-Streams specification RxJava Library 2.0

  • Reactive Streams Reactive Streams is an initiative to provide a standard for

    asynchronous stream processing with non-blocking back pressure. This encompasses efforts aimed at runtime environments (JVM and JavaScript) as well as network protocols.

    asynchronous

  • Java 9 Java 9 Reactive-Streams specification

    Reactive Programming with JDK 9 Flow API https://community.oracle.com/docs/DOC-1006738

    https://community.oracle.com/docs/DOC-1006738

  • interface Publisher { void subscribe(Subscriber
  • Reactive Programming

  • Reactive Programming

    RxJava 2.0

  • RxJava A set of classes for representing sources of data.

    A set of classes for listening to data sources.

    A set of methods for modifying and composing the data.

  • RxJava A set of classes for representing sources of data.

    A set of classes for listening to data sources.

    A set of methods for modifying and composing the data.

  • Sources ()

    synchronous asynchronous

    Source Single item, many items, empty

    error complete

  • 2.0 (Source)

    RxJava 1.0 - Only Observable

    RxJava 2.0 - Observable And Flowable

  • interface Publisher { void subscribe(Subscriber
  • interface Publisher { public void subscribe(Subscriber
  • Flowable vs. Observable Observable 0 ~ n

    complete error

    (backpressure) Flowable

    0 ~ n

    complete error

    (backpressure)

  • Flowable vs. Observable Observable 0 ~ n

    complete error

    Flowable

    0 ~ n

    complete error

  • Reactive-Streams specification

    interface Publisher { void subscribe(Subscriber

  • Flowable vs. Observable Why Flowable and Observable?

  • Flowable vs. Observable Source (Backpressure)

  • Flowable vs. ObservableObservable events = RxView.touches(paintView)

  • Flowable vs. ObservableObservable events = RxView.touches(paintView)

    User (Backpressure)

  • Flowable vs. ObservableObservable events = RxView.touches(paintView)

    Observable rows = db.createQuery("SELECT *")

    User (Backpressure)

  • Flowable vs. ObservableObservable events = RxView.touches(paintView)

    Observable rows = db.createQuery("SELECT *")

    while (cursor.moveToNext()) { // }

  • Flowable vs. ObservableObservable events = RxView.touches(paintView)

    Observable rows = db.createQuery("SELECT *")

    while (cursor.moveToNext()) { // }

    Cursor

  • Flowable vs. ObservableObservable events = RxView.touches(paintView)

    Flowable rows = db.createQuery("SELECT *")

    while (cursor.moveToNext()) { // }

    Design Pattern

  • interface Publisher { public void subscribe(Subscriber
  • interface Publisher { public void subscribe(Subscriber
  • interface Subscriber { void onNext(T t); void onComplete(); void onError(Throwable t); void onSubscribe(Subscription s);} interface Subscription { void cancel(); void request(long r);}

    Observable Flowable

    Flowable vs. Observable

    interface Observer { void onNext(T t); void onComplete(); void onError(Throwable t); void onSubscribe(Disposable d);} interface Disposable { void dispose();}

  • interface Subscriber { void onNext(T t); void onComplete(); void onError(Throwable t); void onSubscribe(Subscription s);} interface Subscription { void cancel(); void request(long r);}

    interface Observer { void onNext(T t); void onComplete(); void onError(Throwable t); void onSubscribe(Disposable d);} interface Disposable { void dispose();}

    Observable Flowable

    Flowable vs. Observable

    Source

  • interface Subscriber { void onNext(T t); void onComplete(); void onError(Throwable t); void onSubscribe(Subscription s);} interface Subscription { void cancel(); void request(long r);}

    interface Observer { void onNext(T t); void onComplete(); void onError(Throwable t); void onSubscribe(Disposable d);} interface Disposable { void dispose();}

    Observable Flowable

    Flowable vs. Observable

    Source

  • interface Subscriber { void onNext(T t); void onComplete(); void onError(Throwable t); void onSubscribe(Subscription s);} interface Subscription { void cancel(); void request(long r);}

    interface Observer { void onNext(T t); void onComplete(); void onError(Throwable t); void onSubscribe(Disposable d);} interface Disposable { void dispose();}

    Observable Flowable

    Flowable vs. Observable

    Source

  • Flowable vs. Observable

    interface Subscriber { void onNext(T t); void onComplete(); void onError(Throwable t); void onSubscribe(Subscription s);} interface Subscription { void cancel(); void request(long r);}

    interface Observer { void onNext(T t); void onComplete(); void onError(Throwable t); void onSubscribe(Disposable d);} interface Disposable { void dispose();}

    Observable Flowable

  • Source Specializations RxJava 2.0 Source

    Source Observable (subsets)

  • Source Specializations RxJava 2.0 Source

    Source Observable (subsets)

    Single - 1 error

    Completable - complete error

    Maybe - 0, 1, complete error

  • Single Succeeds with an item. Errors

    (backpressure)

  • Completable Completes (no items!) Errors

    (backpressure)

  • Maybe Succeeds with an item. Completes with no items. Errors

    (backpressure)

  • Source Specializations RxJava 2.0 Source

    Source Observable (subsets)

    Single - 1 error

    Completable - complete error

    Maybe - 0, 1, complete error

  • Creating SourcesFlowable.just("Hello"); Flowable.just("Hello", "World");Observable.just("Hello");Observable.just("Hello", "World"); Single.just("Hello"); Maybe.just("Hello");

  • Creating SourcesString[] array = {"a", "b"}; List list = new ArrayList(); Flowable.fromArray(array);Flowable.fromIterable(list);Observable.fromArray(array);Observable.fromIterable(list);

  • Creating SourcesFlowable.fromCallable(() -> "Hello");Observable.fromCallable(() -> "Hello"); Single.fromCallable(() -> "Hello"); Maybe.fromCallable(() -> "Hello"); Completable.fromCallable(() -> "Ignore!");

  • Creating SourcesFlowable.fromCallable(() -> "Hello");Observable.fromCallable(() -> "Hello"); Single.fromCallable(() -> "Hello"); Maybe.fromCallable(() -> "Hello"); Maybe.fromAction(() -> System.out.println("Hello"));Maybe.fromRunnable(() -> System.out.println("Hello"));Completable.fromCallable(() -> "Ignore!");Completable.fromAction(() -> System.out.println("Hello"));Completable.fromRunnable(() -> System.out.println("Hello"));

  • Creating SourcesObservable.fromCallable(new Callable() { @Override public String call() throws Exception { return "Hello"; }});

    Returns an Observable that, when an observer subscribes to it, invokes a function you specify and then emits the value returned from that function.

    (subscribe)

  • Creating SourcesObservable.create();

  • Creating SourcesObservable.create(new ObservableOnSubscribe() { @Override public void subscribe(ObservableEmitter e) throws Exception { e.onNext("Hello"); e.onComplete(); }});

  • Creating SourcesObservable.create(new ObservableOnSubscribe() { @Override public void subscribe(ObservableEmitter e) throws Exception { e.onNext("Hello"); e.onComplete(); }});

  • Creating SourcesObservable.create(new ObservableOnSubscribe() { @Override public void subscribe(ObservableEmitter e) throws Exception { e.onNext("Hello"); e.onComplete(); }});

  • Creating SourcesObservable.create(new ObservableOnSubscribe() { @Override public void subscribe(ObservableEmitter e) throws Exception { e.onNext("Hello"); e.onComplete(); }});

  • Creating SourcesObservable.create(e -> { e.onNext("Hello"); e.onComplete();});

  • Creating SourcesObservable.create(e -> { e.onNext(Hello"); e.onNext("World"); e.onComplete();});

    onNext

    (fromCallable onNext)

  • Creating SourcesExecutorService executor = Executors.newSingleThreadExecutor();Observable.create(e -> { executor.submit(() -> { // ... e.onNext(result); e.onComplete(); });});

    background thread onNext async task

  • Creating SourcesOkHttpClient client = // Request request = // Observable.create(e -> { client.newCall(request).enqueue(new Callback() { @Override public void onResponse(Call call, Response response) throws IOException { e.onNext(response.body().toString()); e.onComplete(); } @Override public void onFailure(Call call, IOException ex) { e.onError(ex); } });});

  • Creating SourcesOkHttpClient client = // Request request = // Observable.create(e -> { client.newCall(request).enqueue(new Callback() { @Override public void onResponse(Call call, Response response) throws IOException { e.onNext(response.body().toString()); e.onComplete(); } @Override public void onFailure(Call call, IOException ex) { e.onError(ex); } });});

  • Creating SourcesOkHttpClient client = // Request request = // Observable.create(e -> { client.newCall(request).enqueue(new Callback() { @Override public void onResponse(Call call, Response response) throws IOException { e.onNext(response.body().toString()); e.onComplete(); } @Override public void onFailure(Call call, IOException ex) { e.onError(ex); } });});

  • Creating SourcesOkHttpClient client = // Request request = // Observable.create(e -> { client.newCall(request).enqueue(new Callback() { @Override public void onResponse(Call call, Response response) throws IOException { e.onNext(response.body().toString()); e.onComplete(); } @Override public void onFailure(Call call, IOException ex) { e.onError(ex); } });});

  • Creating SourcesOkHttpClient client = // Request request = // Observable.create(e -> { Call call = client.newCall(request); e.setCancellable(() -> call.cancel()); call.enqueue(new Callback() { @Override public void onResponse(Call call, Response response) throws IOException { e.onNext(response.body().toString()); e.onComplete(); } @Override public void onFailure(Call call, IOException ex) { e.onError(ex); } });});

  • Creating SourcesOkHttpClient client = // Request request = // Observable.create(e -> { Call call = client.newCall(request); e.setCancellable(() -> call.cancel()); call.enqueue(new Callback() { @Override public void onResponse(Call call, Response response) throws IOException { e.onNext(response.body().toString()); e.onComplete(); } @Override public void onFailure(Call call, IOException ex) { e.onError(ex); } });});

    unsubscribe request

  • Creating SourcesButton button = //

    Observable.create(e -> { e.setCancellable(() -> { button.setOnClickListener(null) }); button.setOnClickListener(v -> e.onNext(v));});

  • Creating SourcesButton button = //

    Observable.create(e -> { e.setCancellable(() -> { button.setOnClickListener(null) }); button.setOnClickListener(v -> e.onNext(v));});

    Android memory leak

  • Observing Sources

  • Observing Sources

    interface Subscriber { void onNext(T t); void onComplete(); void onError(Throwable t); void onSubscribe(Subscription s);} interface Subscription { void cancel(); void request(long r);}

    interface Observer { void onNext(T t); void onComplete(); void onError(Throwable t); void onSubscribe(Disposable d);} interface Disposable { void dispose();}

    Observable Flowable

  • Observing Sources

    interface Subscriber { void onNext(T t); void onComplete(); void onError(Throwable t); void onSubscribe(Subscription s);} interface Subscription { void cancel(); void request(long r);}

    interface Observer { void onNext(T t); void onComplete(); void onError(Throwable t); void onSubscribe(Disposable d);} interface Disposable { void dispose();}

    Observable Flowable

  • onSubscribe

    Observing Sources

    interface Subscriber { void onNext(T t); void onComplete(); void onError(Throwable t); void onSubscribe(Subscription s);} interface Subscription { void cancel(); void request(long r);}

    interface Observer { void onNext(T t); void onComplete(); void onError(Throwable t); void onSubscribe(Disposable d);} interface Disposable { void dispose();}

    Observable Flowable

  • interface Subscriber { void onNext(T t); void onComplete(); void onError(Throwable t); void onSubscribe(Subscription s); } interface Subscription { void cancel(); void request(long r);}

    interface Observer { void onNext(T t); void onComplete(); void onError(Throwable t); void onSubscribe(Disposable d); } interface Disposable { void dispose();}

    Observable Flowable

    onSubscribe

    Observer onSubscribe cancel backpressure

    Observing Sources

  • Observing SourcesObservable.just("Hello").subscribe(new Observer() { @Override public void onNext(String value) { } @Override public void onComplete() { } @Override public void onError(Throwable e) { } @Override public void onSubscribe(Disposable d) { }});

  • Observing SourcesObservable.just("Hello").subscribe(new Observer() { @Override public void onNext(String value) { } @Override public void onComplete() { } @Override public void onError(Throwable e) { } @Override public void onSubscribe(Disposable d) { }});

  • Observing SourcesObservable.just("Hello").subscribe(new DisposableObserver() { @Override public void onNext(String value) { } @Override public void onComplete() { } @Override public void onError(Throwable e) { }});

  • Observing SourcesDisposableObserver observer = new DisposableObserver() { @Override public void onNext(String value) { } @Override public void onComplete() { } @Override public void onError(Throwable e) { }}; Observable.just(Hello).subscribe(observer);

  • Observing SourcesDisposableObserver observer = new DisposableObserver() { @Override public void onNext(String value) { } @Override public void onComplete() { } @Override public void onError(Throwable e) { }}; Observable.just(Hello).subscribe(observer);

    // unsubscribe ?

  • Observing SourcesDisposableObserver observer = new DisposableObserver() { @Override public void onNext(String value) { } @Override public void onComplete() { } @Override public void onError(Throwable e) { }}; Observable.just(Hello").subscribe(observer);

    observer.dispose();

  • Observing SourcesObservable o = Observable.just("Hello");

    Disposable d = o.subscribeWith(new DisposableObserver() { @Override public void onNext(String value) { } @Override public void onComplete() { } @Override public void onError(Throwable e) { } });

    d.dispose();

  • Observing SourcesObservable o = Observable.just(Hello");

    Disposable d = o.subscribeWith(new DisposableObserver() { @Override public void onNext(String value) { } @Override public void onComplete() { } @Override public void onError(Throwable e) { } });

    d.dispose();

    New Method: subscribeWith

  • Observing SourcesObservable o = Observable.just(Hello");

    Disposable d = o.subscribeWith(new DisposableObserver() { @Override public void onNext(String value) { } @Override public void onComplete() { } @Override public void onError(Throwable e) { }});

    d.dispose();

    Disposable

  • Observing SourcesObservable o = Observable.just(Hello");

    Disposable d = o.subscribeWith(new DisposableObserver() { @Override public void onNext(String value) { } @Override public void onComplete() { } @Override public void onError(Throwable e) { } });

    d.dispose();

  • Observing SourcesObservable o = Observable.just(Hello);

    CompositeDisposable disposables = new CompositeDisposable();

    disposables.add(o.subscribeWith(new DisposableObserver() { @Override public void onNext(String value) { } @Override public void onComplete() { } @Override public void onError(Throwable e) { }}));

    disposables.dispose();

  • Observing SourcesObservable o = Observable.just(Hello);

    CompositeDisposable disposables = new CompositeDisposable();

    disposables.add(o.subscribeWith(new DisposableObserver() { @Override public void onNext(String value) { } @Override public void onComplete() { } @Override public void onError(Throwable e) { }}));

    disposables.dispose();

  • Observing SourcesObservable o = Observable.just(Hello);

    CompositeDisposable disposables = new CompositeDisposable();

    disposables.add(o.subscribeWith(new DisposableObserver() { @Override public void onNext(String value) { } @Override public void onComplete() { } @Override public void onError(Throwable e) { }}));

    disposables.dispose();

  • Observing SourcesObservable o = Observable.just("Hello"); o.subscribeWith(new DisposableObserver() { });

    Maybe m = Maybe.just("Hello"); m.subscribeWith(new DisposableObserver() { });

    Single s = Single.just("Hello");s.subscribeWith(new DisposableObserver() { });

    Completable c = Completable.completed(Hello"); c.subscribeWith(new DisposableObserver() { });

  • Observing SourcesFlowable f = Flowable.just("Hello");f.subscribeWith(new DisposableSubscriber() { });

    Observable o = Observable.just("Hello");o.subscribeWith(new DisposableObserver() { });

    Maybe m = Maybe.just("Hello");m.subscribeWith(new DisposableObserver() { });

    Single s = Single.just("Hello");s.subscribeWith(new DisposableObserver() { });

    Completable c = Completable.completed(Hello");c.subscribeWith(new DisposableObserver() { });

    Flowable Disposable

  • RxJava A set of classes for representing sources of data.

    A set of classes for listening to data sources.

    A set of methods for modifying and composing the data.

  • OperatorsString normal = "hello"; String upperCase = normal.toUpperCase();

  • OperatorsString normal = "hello"; String upperCase = normal.toUpperCase();

    Observable normal = Observable.just("hello"); Observable upperCase = normal.map(s -> s.toUpperCase());

  • OperatorsObservable.fromCallable(new Callable() { @Override public String call() throws Exception { // ... return result; }});

  • OperatorsObservable.fromCallable(new Callable() { @Override public String call() throws Exception { // ... return result; }}).subscribeOn(Schedulers.computation());

  • OperatorsObservable.fromCallable(new Callable() { @Override public String call() throws Exception { // ... return result; }}).subscribeOn(Schedulers.computation());

    background thread

    bg thread

  • OperatorsObservable.fromCallable(new Callable() { @Override public String call() throws Exception { // ... return result; }}).subscribeOn(Schedulers.computation()) .observeOn(AndroidSchedulers.mainThread()) .subscribe(observer);

    bg thread

  • OperatorsObservable.fromCallable(new Callable() { @Override public String call() throws Exception { // ... return result; }}).subscribeOn(Schedulers.computation()) .observeOn(AndroidSchedulers.mainThread()) .subscribe(observer);

    Observer main thread

    bg thread

    main thread

  • OperatorsObservable.fromCallable(new Callable() { @Override public String call() throws Exception { // ... return result; }}).subscribeOn(Schedulers.computation()) .observeOn(AndroidSchedulers.mainThread()) .subscribe(observer);

    Observer main thread

    main thread

    bg thread

  • OperatorsObservable.fromCallable(() -> { return result;}).subscribeOn(Schedulers.computation()) .observeOn(AndroidSchedulers.mainThread()) .map() .subscribe(observer);

  • OperatorsObservable.fromCallable(() -> { return result;}).subscribeOn(Schedulers.computation()) .observeOn(AndroidSchedulers.mainThread()) .map() .subscribe(observer);

    main thread

  • OperatorsObservable.fromCallable(() -> { return result;}).subscribeOn(Schedulers.computation()) .map() .observeOn(AndroidSchedulers.mainThread()) .subscribe(observer);

  • OperatorsObservable.fromCallable(() -> { return result;}).subscribeOn(Schedulers.computation()) .map() .observeOn(AndroidSchedulers.mainThread()) .subscribe(observer);

    Order

    computation thread

  • OperatorsObservable.fromCallable(() -> { return result;}).subscribeOn(Schedulers.computation()) .map() .subscribeOn(Schedulers.io()) .observeOn(AndroidSchedulers.mainThread()) .subscribe(observer);

  • OperatorsObservable.fromCallable(() -> { return result;}).subscribeOn(Schedulers.computation()) .map() .subscribeOn(Schedulers.io()) .observeOn(AndroidSchedulers.mainThread()) .subscribe(observer);

    computation thread

  • OperatorsObservable.fromCallable(() -> { return result;}).subscribeOn(Schedulers.computation()) .map() .subscribeOn(Schedulers.io()) .observeOn(AndroidSchedulers.mainThread()) .subscribe(observer);

    ?? thread

    computation thread

  • OperatorsObservable.fromCallable(() -> { return result;}).subscribeOn(Schedulers.computation()) .map() .subscribeOn(Schedulers.io()) .observeOn(AndroidSchedulers.mainThread()) .subscribe(observer);

    computation thread

    computation thread

  • OperatorsObservable.fromCallable(() -> { return result;}).subscribeOn(Schedulers.computation()) .map() .subscribeOn(Schedulers.io()) .observeOn(AndroidSchedulers.mainThread()) .subscribe(observer);

    Source subscribeOn subscribeOn schedulers

    computation thread

    computation thread

  • RxJava 1.0 Operator: first() - return Observable takeFirst() - return Observable

    Operators

  • RxJava 1.0 Operator: first() - return Observable takeFirst() - return Observable

    first() element item error

    takeFirst() element item succeed

    Operators

  • RxJava 2.0 Operator: firstOrError() - return Single firstElement() - return Maybe

    Operators

  • RxJava 2.0 Operator: firstOrError() - return Single firstElement() - return Maybe

    BJ4

    Operators

  • Being ReactiveapiService.listToilets()

  • Being ReactiveapiService.listToilets() .subscribeOn(Schedulers.io())

  • Being ReactiveapiService.listToilets() .subscribeOn(Schedulers.io()) .toSortedList(this::compareDistance)

  • Being ReactiveapiService.listToilets() .subscribeOn(Schedulers.io()) .toSortedList(this::compareDistance) .observerOn(AndroidSchedulers.mainThread())

  • Being ReactiveapiService.listToilets() .subscribeOn(Schedulers.io()) .toSortedList(this::compareDistance) .observerOn(AndroidSchedulers.mainThread()) .subscribeWith(new DisposableObserver() { @Override public void onNext(String value) { // Show toilets. } @Override public void onComplete() {/* ignore */} @Override public void onError(Throwable e) {/* show error */} });

  • Being Reactivedisposables.add(apiService.listToilets() .subscribeOn(Schedulers.io()) .toSortedList(this::compareDistance) .observerOn(AndroidSchedulers.mainThread()) .subscribeWith(new DisposableObserver() { @Override public void onNext(String value) { // Show toilets. } @Override public void onComplete() {/* ignore */} @Override public void onError(Throwable e) {/* show error */} }));

  • Being Reactive// onCreate disposables.add(apiService.listToilets() .subscribeOn(Schedulers.io()) .toSortedList(this::compareDistance) .observerOn(AndroidSchedulers.mainThread()) .subscribeWith(new DisposableObserver() { @Override public void onNext(String value) { // Show toilets. } @Override public void onComplete() {/* ignore */} @Override public void onError(Throwable e) {/* show error */} }));

    // onDestory disposables.dispose();

  • Architecture 2.x (stream)

    (stream)

    RxJava

  • RxJava 2 Android UI

  • Reference Exploring RxJava 2 for Android

    https://speakerdeck.com/jakewharton/exploring-rxjava-2-for-android-gotocph-october-2016

    RxJava Official wiki https://github.com/ReactiveX/RxJava/wiki/What's-different-in-2.0

    Reactive-streams API http://www.reactive-streams.org/reactive-streams-1.0.0-javadoc/

    https://speakerdeck.com/jakewharton/exploring-rxjava-2-for-android-gotocph-october-2016https://speakerdeck.com/jakewharton/exploring-rxjava-2-for-android-gotocph-october-2016https://github.com/ReactiveX/RxJava/wiki/What's-different-in-2.0https://github.com/ReactiveX/RxJava/wiki/What's-different-in-2.0

  • Reference Reactive-Streams

    http://www.reactive-streams.org/