从页面/组件中的服务共享相同的Observable

时间:2018-06-18 17:05:37

标签: angular ionic-framework rxjs observable

我正在尝试多次订阅相同的Observable,但它不起作用。我有一个提供商,它从Observable对象中提供AngularFirestore。这是我的提供者:

@Injectable()
export class MyProvider {
  private myObservable: Observable<any>;
  constructor(private aFs: AngularFirestore) {
    //retriving some data and putting in myObservable
  }

  getObservable() {
    return this.myObservable;
  }
}

在我的myPage.ts我这样做:

this.mySubscription = this.myProvider.getObservable().subscribe(value => {
  //something that works
});

在另一个组件中,我也这样做,但它没有给我任何东西。如何从服务或提供商处共享Observable?我尝试了unsubscribe()它,当我从我的页面弹出到组件时,当我在组件上调用unsubscribe()然后导航到我的页面时subscribe()不起作用。

在我的页面中unsubscribe()我做:

ionViewWillLeave() {
  this.mySubscription.unsubscribe();
}

在我的组件中unsubscribe(),在我导航到我的页面之前,我会这样做:

myEvent() {
  this.mySubscription.unsubscribe();
  this.navCtrl.push(MyPage);
}

当我从MyPage弹出时,unsubscribe()似乎正常工作,因为我可以在我的组件中看到myObservable数据。当我尝试从我的组件导航到MyPage时,unsubscribe()似乎不起作用,因为我什么也看不见。我也尝试过调试,但在第二种情况下我无法看到subscribe()

我在app.module.ts下的providers导入我的提供商,然后将其导入我的网页:

MyPage.ts

import { MyProvider } from ..;

构造函数(MyPage.ts):

constructor(private myProvider: MyProvider) {..}

在我的组件中:

MyComponent.ts

import { MyProvider } from ..;

构造函数(Home.ts)

constructor(private myProvider: MyProvider) {..}

我澄清MyComponent中未使用MyPage!我在Home中使用它,然后我用它推送到MyPage。我这样做是因为我想在MyComponent中显示简单数据,然后我想推送到包含数据详细信息的MyPage

我想轻松地从组件和页面上的服务共享相同的Observable,我想在它们上subscribe()。这可能吗?

1 个答案:

答案 0 :(得分:3)

如果您的目标是多播数据,请使用RXJS的SubjectBehaviorSubject
Subject充当源Observable和许多observers之间的桥梁/代理,使多个observers可以共享相同的Observable执行。\ br /> 这种推荐主题的推荐方式是使用asObservable()运算符。

@Injectable()
export class MyProvider {
  private myObservable=new Subject<any>();
  CurrentData = this.myObservable.asObservable();
  constructor(private aFs: AngularFirestore) {
    //your logic
      this.myObservable.next(value);//push data into observable
  }


}

<强> Page.ts

this.mySubscription = this.myProvider.CurrentData.subscribe(value => {
      //something that works
    });

使用行为主题

 @Injectable()
    export class MyProvider {
      private myObservable=new BehaviorSubject<any>('');
      CurrentData = this.myObservable.asObservable();
      constructor(private aFs: AngularFirestore) {

      }

     getData(myParam): void { 
       someasynccall.pipe(map(),filter()).
          subscribe(value=>this.myObservable.next(value))


    }

<强> Page.ts

this.myProvider.getData(param);
this.mySubscription = this.myProvider.CurrentData.subscribe(value => {
      //something that works
    });

<强> Subject vs BehaviorSubject

<强> LiveDemo