我有一个Angular 7模板,该模板展示了一个具有可观察性translationsAsArray$
作为成员的可观察性<div *ngIf="book$ | async as book">
<dl>
<div *ngIf="(book.translationsAsArray$ | async) as translations">
<dt><b class="text-muted">TRANSLATIONS</b></dt>
<dd>
<ul class="list-unstyled">
<li *ngFor="let translation of translations">
<a routerLink="/books/{{translation.rid}}">{{translation.title}}</a> ({{translation.languageAsString}})
</li>
</ul>
</dd>
</div>
</dl>
</div>
:
book.translationsAsArray$
编辑: get translationsAsArray$(): Observable<Book[]> {
return timer(50).pipe(
tap(time => console.log('translationsAsArray$() subsribed')),
map(time => [new Book(this.bookService, 'abc')]));
}
如下所示(仅出于测试目的):
translationsAsArray$
我遇到的问题是subscribe
被反复重新订阅。
当我将解决方案更改为在组件打字稿中调用async
而不是对book$
和translationsAsArray$
使用{{1}}管道时,问题就解决了。
您知道原因吗?我的模板应该看起来有所不同吗?
答案 0 :(得分:0)
防止这种情况发生的一种技巧是创建一个模板变量对象,并将所有可观察对象作为属性,并使用它来控制模板:
<div *ngIf="{ book: (book$ | async), translations: (term.translationsAsArray$ | async) } as asyncs"
<div *ngIf="asyncs.book">
<dl>
<div *ngIf="asyncs.translations">
<dt><b class="text-muted">TRANSLATIONS</b></dt>
<dd>
<ul class="list-unstyled">
<li *ngFor="let translation of asyncs.translations">
<a routerLink="/books/{{translation.rid}}">{{translation.title}}</a> ({{translation.languageAsString}})
</li>
</ul>
</dd>
</div>
</dl>
</div>
</div>
答案 1 :(得分:0)
您的getter方法get translationsAsArray$()
每次被调用时都会返回一个新的Observable对象。 Angular的async
管道会看到一个新的对象引用,因此它订阅了新的observable。
get observableObj() {
// Returns a new object each time
return timer(50);
}
constructor() {
console.log('Testing Observable reference equality');
const obj1 = this.observableObj;
const obj2 = this.observableObj;
console.log('Different Object references?', obj1 !== obj2); // true
}
您需要确保Observable对象引用保持不变。
为此,请将getter更改为常规对象属性:
book.translationsAsArray$ = timer(50).pipe(
tap(time => console.log('translationsAsArray subscribed')),
map(time => ['abc'])
)
如果translationsAsArray$
必须是一个吸气剂,则应缓存返回对象,以免每次都不返回新的对象引用。