簡體   English   中英

RxJava:鏈接可觀察量

[英]RxJava: chaining observables

是否可以使用RxJava實現下一個鏈接:

loginObservable()
   .then( (someData) -> {
      // returns another Observable<T> with some long operation
      return fetchUserDataObservable(someData);

   }).then( (userData) -> {
      // it should be called when fetching user data completed (with userData of type T)
      cacheUserData(userData);

   }).then( (userData) -> {
      // it should be called after all previous operations completed
      displayUserData()

   }).doOnError( (error) -> {
      //do something
   })

我發現這個庫非常有趣,但無法想象我們如何將請求鏈接到彼此依賴於之前的地方。

當然,RxJava支持.map這樣做。 來自RxJava Wiki:

地圖

基本上,它是:

loginObservable()
   .switchMap( someData -> fetchUserDataObservable(someData) )
   .map( userData -> cacheUserData(userData) )
   .subscribe(new Subscriber<YourResult>() {
        @Override
        public void onCompleted() {
           // observable stream has ended - no more logins possible
        }
        @Override
        public void onError(Throwable e) {
            // do something
        }
        @Override
        public void onNext(YourType yourType) {
            displayUserData();
        }
    });

這是Googling RxJava鏈可觀察量的最高職位,因此我將添加另一個常見情況,您不希望轉換您收到的數據,但將其與另一個操作鏈接(例如,將數據設置為數據庫)。 使用.flatmap() 這是一個例子

    mDataManager.fetchQuotesFromApi(limit)
            .subscribeOn(mSchedulerProvider.io())
            .observeOn(mSchedulerProvider.ui())
            .onErrorResumeNext(Function { Observable.error<List<Quote>>(it) }) //OnErrorResumeNext and Observable.error() would propagate the error to the next level. So, whatever error occurs here, would get passed to onError() on the UI side
            .flatMap { t: List<Quote> ->
                //Chain observable as such
                mDataManager.setQuotesToDb(t).subscribe({}, { e { "setQuotesToDb() error occurred: ${it.localizedMessage}" } }, { d { "Done server set" } })
                Observable.just(t)
            }
            .subscribeBy(
                    onNext = {},
                    onError = { mvpView?.showError("No internet connection") },
                    onComplete = { d { "onComplete(): done with fetching quotes from api" } }
            )

這是RxKotlin2,但RxJava和RxJava2的想法是一樣的:

快速解釋:

  • 我們嘗試使用mDataManager.fetchQuotesFromApi()從api獲取一些數據(在本例中為引號mDataManager.fetchQuotesFromApi()
  • 我們訂閱了observable來在.io()線程上做東西並在.ui()線程上顯示結果。
  • onErrorResumeNext()確保在此方法中捕獲從獲取數據中遇到的任何錯誤。 我想在那里出現錯誤時終止整個鏈,所以我返回一個Observable.error()
  • .flatmap()是鏈接部分。 我希望能夠將從API獲得的任何數據設置到我的數據庫中。 我沒有使用.map()轉換我收到的數據,我只是在改變它的情況下使用該數據做其他事情
  • 我訂閱了最后一個可觀察鏈。 如果在獲取數據時出現錯誤(第一個可觀察的),則會使用onErrorResumeNext()處理它(在這種情況下,傳播到訂閱的onError() onErrorResumeNext()
  • 我非常清楚我正在訂閱DB observable(在flatmap()內部)。 通過此observable發生的任何錯誤都不會傳播到最后的subscribeBy()方法,因為它是在.flatmap()鏈內的subscribe()方法內處理的。

代碼來自這個項目 ,位於: https//github.com/Obaied/Sohan/blob/master/app/src/main/java/com/obaied/dingerquotes/ui/start/StartPresenter.kt

嘗試使用scan()

Flowable.fromArray(array).scan(...).subscribe(...)

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM