在自定义Application子类中使用Observable

时间:2014-05-17 12:45:03

标签: android reactive-programming rx-java

在自定义Application子类中创建Rx Observable是否可以接受。这样做的原因是,我可以在Application中创建BehaviorSubject,并且每隔10分钟就要求从服务器进行更改,订阅此Observable的每个Activity或Fragment将只获得最后的更改状态。

问题是这个架构在应用程序生命周期处理方面是否可以被认为是安全的并且易于使用?

class CustomApplication extends Application {
   ...

   BehaviorSubject<Friends> mFriends = new BehaviorSubject<Friends>;
   public void createObservables() {
      Observable.create(new Observable.OnSubscribe<Friends>() {
         public void call(Subscriber<?> s) {
            while(true) {
               mFriends.onNext("randomFriendN");
               sleep(10sec);
            }
         }
      })
      .subscribeOn(Schedulers.newThread())
      .subscribe(new Observer<List<NewsCategory>>() {
         public void onNext(Friends f) { //empty }
      });
   }
   public BehaviorSubject<Friends> getFriends() {
      return mFriends;
   }
}

更新 每次创建新活动并且想要获取数据时,它都可以获得ApplicationContext的BehaviorSubject然后订阅它,并且Subject将发出最后发出的值; 我为什么要这样做?例如。让我们说你有新闻项目,你提取新闻源,你想开始提取新闻项目全部内容的后台任务,在这种情况下,我可以在滚动新闻列表时开始获取数据,当你点击详细活动时,我们可以显示它已经取出,或者只是下载它。

1 个答案:

答案 0 :(得分:2)

我认为只要在应用程序初始化期间只调用一次createObservables(),这就完全安全了。一些建议的改变......

我不会在getFriends()的返回值中公开mFriends的BehaviorSubject部分。这样,getFriends()的调用者就不会想要调用onNext()。将其更改为:

public Observable<Friends> getFriends() {
    return mFriends;
}

如果您想要超级安全,请使用.asObservable(),并且调用者甚至无法将返回值强制转换回BehaviorSubject。

public Observable<Friends> getFriends() {
    return mFriends.asObservable();
}

我还会更新你的createObservable()方法,从subscribe回调中调用BehaviorSubject onNext()。这是您的代码稍作修改后使用NewsItems。

BehaviorSubject<List<NewsItem>> mNewsItemSubject = BehaviorSubject.create();

void createObservables() {
    Observable
            .timer(10, 10, TimeUnit.SECONDS, Schedulers.newThread())
            .flatMap(new Func1<Long, Observable<List<NewsItem>>>() {
                @Override
                public Observable<List<NewsItem>> call(Long aLong) {
                    // Normally you would create a network API that returns Observable<NewsItem>.
                    // For now just pretend this returned Observable makes an Observable
                    // network request.
                    return Observable.just(
                            Arrays.asList(
                                    new NewsItem("fakeNewsItem"),
                                    new NewsItem("fakeNewsItem1")
                            )
                    );
                }
            })
            .subscribe(new Action1<List<NewsItem>>() {
                @Override
                public void call(List<NewsItem> newsItems) {
                    mNewsItemSubject.onNext(newsItems);
                }
            });
}

public Observable<List<NewsItem>> observeNewsItems() {
    return mNewsItemSubject;
}

然后,您的Android活动可以调用((CustomApplication)getApplication())。observeNewsItems()以在活动可见时获取最新新闻和任何更新。

final Observable<List<NewsItem>> newsItemsObservable = 
    ((CustomApplication) getApplication()).observeNewsItems();

newsItemsObservable
        .observeOn(AndroidSchedulers.mainThread())
        .subscribe(new Observer<List<NewsItem>>() {
            @Override
            public void onCompleted() {
                // All done.
            }

            @Override
            public void onError(Throwable e) {
                // Notify user of error (maybe)
            }

            @Override
            public void onNext(List<NewsItem> newsItems) {
                // Update the UI with newsItems.
            }
        });