首页
学习
活动
专区
工具
TVP
发布
社区首页 >问答首页 >在线路守卫中订阅观察者及其意义

在线路守卫中订阅观察者及其意义
EN

Stack Overflow用户
提问于 2018-10-23 03:06:35
回答 1查看 956关注 0票数 4

我有一个名为PermissionGuard的路由器保护,它在这里启动

代码语言:javascript
复制
const routes: Routes = [
  {
    path: ':company',
    component: CompanyComponent,
    canActivate: [PermissionGuard],
    canActivateChild: [PermissionGuard],
    children: [
      {
        path: '',
        component: IndexComponent
      },
      {
        path: 'projects',
        loadChildren: '../projects/projects.module#ProjectsModule'
      },
    ]
  }
];

在我的PermissionGuard中,我订阅了这样的PermissionService

代码语言:javascript
复制
export class PermissionGuard implements CanActivate, CanActivateChild {

  private permissions: Permission[];

  constructor(private permissionService: PermissionService, private router: Router) {
    this.permissionService.permissions$.subscribe(
      (permissions: Permission[]) => {
        this.permissions = permissions;
      }
    );
  }

  canActivate(next: ActivatedRouteSnapshot, state: RouterStateSnapshot): Observable<boolean> {
    this.permissionService.getPermissions(next.paramMap.get('company'));
    return this.permissionService.permissionsFetchDone$
    .pipe(filter(x => x))
    .pipe(
      map(response => {
        if (this.permissions) {
          return true;
        } else {
          this.router.navigate(['/forbidden']);
        }
      })
    );
  }
}

并基于该数据执行必要的canActivatecanActivateChild检查。通过在子路由中添加console.log()和从permissions$发出新数据,我可以看到可观察值仍然是活动的,即使守卫已经“使用”并且路由已被激活。然后,我希望当我到path: ':company'外的一条路线时,它会消失,但是这个守卫并没有被摧毁。

这就引出了我的问题:,我这样做正确吗?我希望使用保护来检查用户是否有任何权限,但同时我希望只执行一次权限的HTTP请求(当导航到path: ':company'或其任何子项时)。我担心,如果我使用这样的守卫,由于大量的观察者,最终会减慢整个应用程序的运行速度。

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2018-10-23 03:39:39

从子路由内的权限$发出新数据我可以看到,即使守卫已被“使用”并且路由已被激活,但可观察性仍然是活动的。

首先,permissions$仍然是活动的,因为你从来没有在你的守卫中取消订阅。并且angular创建了一个单例的守卫。

即使guard不是单例的,guard的实例仍然通过this.permissions在订阅中被引用,并且如果您的observable作为变量存在于您的身份验证服务中(我假设它是一个单例),此绑定也会阻止垃圾收集。

这就引出了我的问题:我这样做正确吗?我希望使用守卫来检查用户是否有权限。

在你的守卫下发出一个请求是完全没问题的,比如为了获得权限。

,但同时我只想执行一次权限的HTTP请求(当导航到path:':company‘或它的任何子级时)。

如果您只想发出一次请求,那么您应该考虑在身份验证服务中使用shareReplay,以便将来连接的所有实例都使用先前发出的相同值。

票数 3
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/52936191

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档