我的Angular2 / Firebase应用中的组件中包含以下代码:
ngOnInit() {
this.allItems = this.angularFireDatabase.object(`projects/${id}/results`).map(
results => {
const x = itemMapper(results);
console.log(x); // <-- executes three times
return x;
});
const groupedData = this.allItems.map(groupMapper);
this.towers = groupedData.map(towerMapper);
this.units = groupedData.map(unitMapper);
}
我在this.allItems
管道的模板中使用this.towers
,this.units
和async
:
<sanddance [items]="allItems | async">
<p-dataTable [value]="towers | async">
<p-dataTable [value]="units | async">
代码运行正常,但问题是日志执行了三次 - 换句话说,创建this.allitems
的映射运行了三次。如果我删除了this.towers
和this.units
分配,则日志只会按预期执行一次。换句话说,this.towers = groupedData.map(towerMapper);
行似乎会导致额外调用创建this.allItems
的映射器,尽管它不应该而且我不想要它。它甚至可以重新访问Firebase数据库中的数据,这显然是一个问题,特别是因为这是很多数据?
基于我对&#34; hot&#34;的有限理解和&#34;冷&#34; observables,似乎AngularFire observable被视为&#34; hot&#34;,当有人下游尝试映射它时(或者订阅它,这基本上是async
管道所做的事情时重新触发) )。
我错过了什么?
答案 0 :(得分:1)
AngularFire2可观测量是冷观测值。每个订阅都会看到内部创建的单独的Firebase Reference
- 然后附加了侦听器等。
当您的代码段中的组合可观察对象被订阅时,每个都将影响对AngularFire2 object
可观察对象的订阅。如果您希望使用单个订阅,则可以使用share
运算符:
import 'rxjs/add/operator/share';
this.allItems = this.angularFireDatabase.object(`projects/${id}/results`).map(
results => {
const x = itemMapper(results);
console.log(x); // <-- this should execute only once
return x;
}).share();
const groupedData = this.allItems.map(groupMapper);
this.towers = groupedData.map(towerMapper);
this.units = groupedData.map(unitMapper);
share
运算符:
返回一个新的Observable,它可以多播(共享)原始的Observable。只要至少有一个订阅者,此Observable将被订阅并发送数据。当所有订阅者都取消订阅时,它将取消订阅源Observable。因为Observable是多播,所以它使流变热。这是
的别名.publish().refCount().