我创建了一个Observable:
public getData(): Observable<any> {
return this.getEndpoint()
.pipe(
switchMap((endpoint) =>
this.http.get<any>(endpoint)
),
take(1)
);
}
我订阅了observable,HTTP调用被执行
this.getData().subscribe({
next: data => this.data = data,
complete: () => {
this.someActions();
},
});
由于Observable管道中的take(1(,可观测在一个发射值之后完成。因此,在我们执行某些Actions((的地方调用完整的方法。由于此方法是自定义的,订阅是自行取消订阅,还是必须在完整方法中手动取消订阅?
编辑:如何以完整的订阅方式取消订阅?
您永远不需要取消订阅已完成的可观察对象。可观察器通过对其观察器的complete((或error((调用来完成。这是可观测的合同的一部分。
请考虑以下示例。
const sub = interval(250).pipe(
take(4),
map(x => x + 1)
).subscribe({
next: console.log,
complete: () => console.log("This observable completed naturally"),
err: _ => console.log("This observable completed with an error")
});
console.log("Sub is closed, no need to unsubscribe? " + sub.closed);
setTimeout(() => {
console.log("Sub is closed, no need to unsubscribe? " + sub.closed);
}, 1250);
控制台输出:
Sub is closed, no need to unsubscribe? false
1
2
3
4
This observable completed naturally
Sub is closed, no need to unsubscribe? true
这表明将完成的可观测性不需要取消订阅,也不会造成内存泄漏。问题在于长寿命的可观察性(比如没有take
、takeWhile
、takeWhen
等运算符的区间(。
例如,在角度中,一些可观察性需要在组件存在的时间内存在,但不再存在。它们与组件生命周期相关联。问题是,忘记取消订阅这样的可观察性(本身不complete
的可观察性(会导致内存泄漏。
同步示例:
of("Hello There").subscribe({
next: console.log,
complete: () => console.log("This observable completed naturally"),
err: _ => console.log("This observable completed with an error")
});
您不需要取消订阅此观察。事实上,因为它是同步运行的,所以在您取消订阅之前,它将被关闭。
const sub = of(1).subscribe();
console.log(sub.closed); // output: true
取消订阅必填示例:
const sub = interval(1000).subscribe(console.log);
setTimeout(() => {
console.log("Sub is closed: " + sub.closed);
sub.unsubscribe();
console.log("Sub is closed: " + sub.closed);
}, 60 x 60 x 1000);
在这里,我们开始一个可观察的,然后等待一个小时,看看它是否关闭。然后我们取消订阅并检查它是否已关闭。此间隔将永远运行,直到明确取消订阅为止。
控制台输出:
0
1
2
... [skipping ahead]
3596
3597
3598
3599
Sub is closed: false
Sub is closed: true