14

canActivate在 Angular2 中配置路由时,有没有办法设置“基础” ?这样所有的路由都被同一个base check覆盖,然后每条路由都可以进行更细粒度的检查。

我有一个AppModule这样的路由:

@NgModule({
    imports: [
        RouterModule.forRoot([
            {
                path: '',
                component: HomeComponent,
                canActivate: [AuthenticationGuardService],
                data: { roles: [Roles.User] }
            }
        ])
    ],
    exports: [
        RouterModule
    ]
})
export class AppRoutingModule { }

对于功能模块FeatureModule

@NgModule({
    imports: [
        RouterModule.forChild([
            {
                path: "feature",
                component: FeatureComponent,

                // I'd like to avoid having to do this:
                canActivate: [AuthenticationGuardService],
                data: { roles: [Roles.User] }
            }
        ])
    ],
    exports: [
        RouterModule
    ]
})
export class FeatureRoutingModule { }

我让AuthenticationGuardService检查用户是否可以使用data.

我可以做些什么来避免在我的所有功能路由模块中进行设置canActivatedata?我只想canActivate为此应用程序中的所有路由配置一个“基础”。

4

2 回答 2

11

我已经编写了一个解决方案,可以为我的应用程序的每个路由(包括由子模块定义的路由)动态添加 Guard。

我在阅读此 Router Docs时想出了这个解决方案。

编辑

这是一个活的StackBlitz示例。

const routes: Routes = [
  { path: '', redirectTo: 'home', pathMatch: 'full' },
  { path: 'login', component: LoginComponent, data: { skipGuard: true } },
  { path: '403', component: ForbiddenComponent, data: { skipGuard: true } },
  { path: '**', component: NotFoundComponent, data: { skipGuard: true } }
];

@NgModule({
  imports: [RouterModule.forRoot(routes)],
  exports: [RouterModule],
  providers: []
})
export class AppRoutingModule {
  
  constructor(router: Router) {
    router.config
        .filter(route => !route.data || !route.data.skipGuard)
        .forEach(route => this.addGuard(route));
  }
  
  private addGuard(route: Route): void {
    route.canActivate = route.canActivate ? 
                   [AuthGuard].concat(route.canActivate) : [AuthGuard];
    route.canActivateChild = route.canActivate ? 
                   [AuthGuard].concat(route.canActivate) : [AuthGuard];
  }
}

于 2018-02-02T18:31:08.117 回答
9
const routes: Routes = [
  {
    path: '',
    canActivate: [AuthGuard],
    children: [
      { path: '', component: HomeComponent },
      { path: 'builds', component: BuildsComponent },
      { path: 'files', component: FilesComponent },
      { path: 'publications', component: PublicationsComponent }
    ]
  },
  { path: 'login', component: LoginComponent },
  { path: '**', redirectTo: '' }
];
于 2016-12-15T12:38:39.830 回答