首页 新闻 会员 周边 捐助

angular 中订阅 router events 是否需要 unsubscribe

0
悬赏园豆:30 [待解决问题]

比如下面的订阅 NavigationStart 事件的代码,通过 RxHelper.autoUnsubscribe 进行了 unsubscribe,请问这个退订是否必要?

this._router.events
    .pipe(
        filter(ev => ev instanceof NavigationStart),
        debounceTime(100),
        this._rxHelper.autoUnsubscribe
    )
    .subscribe((ev) => {
        this.setActiveTab(ev.url)
    });
问题补充:

stackoverflow 上的相关回答:

dudu的主页 dudu | 高人七级 | 园豆:28665
提问于:2025-01-10 07:43
< >
分享
所有回答(2)
0

这篇博文 Subscriptions & practices to avoid in Angular 中说需要 unsubscribe

You can be completely confident that your subscription will complete without any extra maintenance, but if a user accidentally clicks into one route, and immediately clicks out before a request completes, or an observable accomplishes it’s task, then you can end up with that subscription running until the app is refreshed.

提问中的代码是只在 AppComponent 中加载一次的 AppLayoutTabComponent 中用到的,应该可以不需要 unsubscribe

dudu | 园豆:28665 (高人七级) | 2025-01-10 08:17

如果需要 unsubscribe,可以使用 takeUntilDestroy ,详见 takeUntilDestroy in Angular v16

支持(0) 反对(0) dudu | 园豆:28665 (高人七级) | 2025-01-10 08:35

通过这篇博文 Goodbye to unsubscribe in Angular components 确认不需要 unsubscribe

The ActivatedRoute and its observables are insulated from the Router itself so the Angular Router destroys a routed component when it is no longer needed and the injected ActivatedRoute dies with it. No need to unsubscribe from the activated route.

支持(0) 反对(0) dudu | 园豆:28665 (高人七级) | 2025-01-10 11:43
0

在 Angular 中,订阅 Router 的事件(如 NavigationStart)时,是否需要手动取消订阅(unsubscribe)取决于你的使用场景和组件的生命周期。以下是一些需要考虑的因素:

1. 组件的生命周期

如果你的订阅是在一个组件中创建的,并且该组件在某些情况下可能会被销毁(例如,路由变化导致组件卸载),那么在组件销毁时取消订阅是非常重要的。这可以防止内存泄漏和潜在的错误,因为组件可能会在订阅仍然活动的情况下被销毁。

2. 使用 autoUnsubscribe

在你的代码中,使用了 this._rxHelper.autoUnsubscribe,这通常是一个自定义的操作符或方法,用于自动处理取消订阅。假设这个方法在组件销毁时会自动调用 unsubscribe,那么在这种情况下,你不需要手动取消订阅。

3. Angular 的 AsyncPipe

如果你在模板中使用 AsyncPipe 来处理 Observable,Angular 会在组件销毁时自动取消订阅。因此,在这种情况下,也不需要手动取消订阅。

4. 性能和资源管理

即使在某些情况下不需要手动取消订阅,良好的实践是始终在不再需要时取消订阅,以确保资源得到有效管理,避免不必要的内存占用。

结论

  • 如果 this._rxHelper.autoUnsubscribe 确保在组件销毁时正确地取消订阅,那么在这种情况下,手动取消订阅是不必要的。
  • 如果没有自动取消的机制,那么在组件的 ngOnDestroy 生命周期钩子中手动取消订阅是必要的。

示例代码

如果你需要手动取消订阅,可以这样做:

import { Component, OnDestroy } from '@angular/core';
import { Router, NavigationStart } from '@angular/router';
import { Subscription } from 'rxjs';
import { filter, debounceTime } from 'rxjs/operators';

@Component({
  // ...
})
export class MyComponent implements OnDestroy {
  private subscription: Subscription;

  constructor(private _router: Router) {
    this.subscription = this._router.events
      .pipe(
        filter(ev => ev instanceof NavigationStart),
        debounceTime(100)
      )
      .subscribe((ev: NavigationStart) => {
        this.setActiveTab(ev.url);
      });
  }

  ngOnDestroy() {
    if (this.subscription) {
      this.subscription.unsubscribe();
    }
  }

  setActiveTab(url: string) {
    // ...
  }
}

如果你的 autoUnsubscribe 方法已经处理了这一点,你就可以放心地使用它。

Technologyforgood | 园豆:7793 (大侠五级) | 2025-01-10 15:52
清除回答草稿
   您需要登录以后才能回答,未注册用户请先注册