我需要取消订阅 Angular Observable 吗? [复制]
Posted
技术标签:
【中文标题】我需要取消订阅 Angular Observable 吗? [复制]【英文标题】:Do I need to unsubscribe from an Angular Observable? [duplicate] 【发布时间】:2022-01-02 16:01:39 【问题描述】:对于是否以及何时您应该退订 Angular Observable,很难得到一个直接的答案。
我有以下场景:
this.subscription = this.service.makeHTTPCall(stuff).subscribe(x =>
//do something
);
我看到了一些解决方案:
不要将订阅存储为变量,这是否意味着我不必取消订阅?
this.service.makeHTTPCall(stuff).subscribe(x =>
//do something
);
将订阅存储为变量并在 ngOnDestroy 中取消订阅
ngOnDestroy()
if (this.subscription) this.subscription.unsubscribe();
什么都不做,Angular 会为你整理所有退订的东西
我知道有像ng-take-until-destroy
这样的第三方库,但假设我们没有任何第三方库,这是建议的退订方法吗?
【问题讨论】:
【参考方案1】:对于一些冷的 observable,您不需要手动取消订阅,因为它们会发出一次,然后立即完成。 http 服务就是这种 observable 的一个例子。
话虽如此,如果如果你不知道 observable 是否会发出一次并立即完成,那么你应该始终进行适当的清理。
就个人而言,我更喜欢使用take(1)
运算符,它会收到第一个响应,然后自行取消订阅:
someObs.pipe(take(1)).subscribe(...)
【讨论】:
【参考方案2】:您无需手动取消订阅 HTTP Observable 和 Router observable。对于所有其他订阅者,最佳实践是创建一个主题 destroy$,然后使用 rxjs 管道 takeUntil() 获取所有订阅者,直到 destroy$ 处于活动状态。在 ngOnDestroy 中,您在 destroy$ 主题中发出 true 并取消订阅。所有其他订阅者将一起停止。 Angular 不会为您整理所有取消订阅的内容,您应该自己做。它可以提供许多可硬调试的错误,以便在组件销毁后留下 gost 订阅者。下面是示例代码:
onDestroy$: Subject<boolean> = new Subject();
ngOnInit()
this.service.someSubscriber.pipe(takeUntil(this.destroy$)).subscribe(() =>
//do stuff
)
this.service.someSubscriber2.pipe(takeUntil(this.destroy$)).subscribe(() =>
//do stuff
)
this.service.someSubscriber3.pipe(takeUntil(this.destroy$)).subscribe(() =>
//do stuff
)
ngOnDestroy()
this.destroy$.next(true);
this.destroy$.unsubscribe();
在html模板中,异步管道会自动触发取消订阅,所以当你使用它时你可以不用担心它。
【讨论】:
【参考方案3】:您无需手动取消订阅 HTTP Observable 和 Router observable。除了这两个之外,您创建的任何主题或可观察对象都已使用您已经提到的一种方式手动取消订阅,另一种方式可以使用 async
运算符。异步运算符会自动为您取消订阅,也可以使用另一种方式使用 @987654323 @运算符
来自https://***.com/a/41177163/2987066
TLDR:
对于这个问题,有 (2) 种 Observables - 有限值 和无限的价值。
http Observables 产生有限 (1) 个值和类似 DOM 的东西 事件监听器 Observables 产生无限的值。
如果您手动调用订阅(不使用异步管道),那么 取消订阅无限的 Observables。
不用担心有限的,RxJs 会处理它们的。
【讨论】:
以上是关于我需要取消订阅 Angular Observable 吗? [复制]的主要内容,如果未能解决你的问题,请参考以下文章
我需要取消订阅 Angular Observable 吗? [复制]
我们是不是需要取消订阅 Angular 中的 http 调用? [复制]
Angular 2 - 订阅 FormControl 的 valueChanges 是不是需要取消订阅?