嵌套的Observables:添加一个observable作为一个observable的属性并将其展开

时间:2017-03-07 15:37:37

标签: angular firebase rxjs angularfire2

我正在尝试创建一个函数,将用户数据作为Observable并使用来自第一个observable的数据从查询中添加/合并数据,然后将所有这些数据作为一个observable返回,我可以这样做,但不能对返回嵌套的observable

这是一个函数,它返回一个带有observable的observable作为属性,名为holidays

a5d6f33

当我打电话试图取出假日存储的数据时出现问题

getAllUsersWithHolidays() {
  return this.users.map(items => {
   for (let item of items) {
    item.holiday = this.af.database.list('Holiday',
      {
        query: {
          orderByChild: 'userIdKey',
          equalTo: item.$key
        }
      }
    )
   }
  return items;
 });
}

然后用异步

打开
this.summary$ = this.UserListService.getUserByEmail().mergeMap(user => { //get the user details to filter by team
  return this.HolidayService.getAllUserWithHolidays().map(data => {
    return data
    .filter(team => team.team === user[0].team) //filters users by team
    .map(item => { //map over combined data
      return item.holiday
      .map(hol => { // Hol is observable, build with property daysTaken
          return {
            firstname: item.firstname,
            surname: item.surname,
            holiday: hol.reduce((prev, curr) => {prev + curr.daysTaken, 0) //cannot access hol data        
          }
      });         
    });
  })
})

当映射假日可观察时,似乎我无法访问数据?也许是因为我没有订阅?

我宁愿没有一个observable作为从getAllUsersWithHolidays返回的属性我宁愿先计算它

所以代替这个返回项目

 {{summary$ | async | json}}

我会把它计算回来

{user: 'exampleName', holiday:fireBaseListObservable}

但这样做也让我无法实现......

{ user:'exampleName' , holiday: 20 }

我以为我可以这样做,但是这仍然会返回一个可观察的,当然我不能在这里订阅并返回任何东西,这似乎永远不会起作用!

2 个答案:

答案 0 :(得分:0)

我认为你有一个可观察的流可以发出可观察的信息。听起来很可怕,但不要担心,RxJS可以解决这个问题。

顶级可观察流称为高阶可观察流。被发射的可观察物称为内部可观察物。

要获取从内部observable(而不是内部observable本身)发出的值,您应该使用switchMap。

switchMap比flatMap更友好,因为如果有一个优秀的innerObservable,切换图将取消它,而是从最新的内部可观察对象发出。这对于http observables来说非常方便。

flatMap不会取消以前的流,因此您会发现所有内部可观察数据的发出。

答案 1 :(得分:0)

当您使用mergeMap从getUsers展开嵌套的observable时 - > usersWithHolidays,您只需要额外的mergeMap即可为每个用户展开假期。唯一的复杂因素是嵌套的observable是对象的属性。所以我们可以使用Observable.from()来处理它。

getAllUsersWithHolidays() {
  return this.users.mergeMap(items => {
   return Observable
       .from(items)
       .mergeMap(item => this.af.database.list(...)
          .map(holiday => {
               return {
                  ...item,
                  holiday
               };
           })
       );
  });
}