【问题标题】:Configure Route Guard配置路由保护
【发布时间】:2018-08-30 04:08:13
【问题描述】:

我有一个需要配置的路由保护。在某些路线上,我们想检查我们的user client 是否准备好,在其他一些路线上,我们想检查我们的team client 是否准备好等等。

我的路线守卫看起来像这样

@Injectable({
    providedIn: 'root'
})
export class ClientReadyGuard implements CanActivate, CanActivateChild {
    constructor(
        private clientName: string,
        private router: Router ,        
        private apolloState: ApolloStateService,

    ) {
        debugger;
    }

    canActivate(...) {
       // do things with clientName
    }

从这个守卫我想要多个守卫:一个用clientName'all-users'保护,一个用'user'保护,一个用'team'保护,等等。

拥有:

canActivate: [
   AllUserClientReadyGuard,
   UserClientReadyGuard,
   TeamClientReadyGuard,

]

为此,我尝试了注入令牌,但没有成功; (NullInjectorError: No provider for InjectionToken router token!)。

export const ROUTER_TOKEN = new InjectionToken<Router>('router token');
export const APOLLO_STATE_TOKEN = new InjectionToken<ApolloStateService>('apollo state token');


export const UserClientReadyGuard = new InjectionToken<ClientReadyGuard>(
    'user client ready guard',
    {
        providedIn: 'root', factory: () => new ClientReadyGuard(
            USER_CLIENT,
            inject(ROUTER_TOKEN),
            inject(APOLLO_STATE_TOKEN),
        )
    }
);

【问题讨论】:

    标签: angular angular-routing angular-router-guards


    【解决方案1】:

    我最终使用了继承。不过,从路由器使用{ data } 通常可以说是一个更好的选择。但是由于我最终需要扩展警卫的不同行为,因此我可以覆盖方法。我想这取决于大小写。

    export abstract class ClientReadyGuard implements CanActivate, CanActivateChild {
    
        constructor(
            protected router: Router,
            protected apolloState: ApolloStateService,
            protected client: string
        ) { }
    
        canActivate(route: ActivatedRouteSnapshot): boolean | Observable<boolean> | Promise<boolean> {
            return this.checkReady(this.client);
        }
    
    
        protected checkReady(client: string): Observable<boolean> {
            //...
        }    
    }
    
    @Injectable({
        providedIn: 'root'
    })
    export class GlobalDataClientReadyGuard extends ClientReadyGuard {
        constructor(
            protected router: Router,
            protected apolloState: ApolloStateService,
        ) {
            super(router, apolloState, GLOBAL_DATA_CLIENT);
        }
    }
    

    【讨论】:

    • 我认为使用data 一点也不好,我很恼火的是,这在 Angular 社区中作为“最佳实践”越来越受欢迎。 data 具体有两个陷阱。 1) 多个守卫可能出于不同的原因希望在data 对象上使用相同的属性,从而导致冲突。 2) 使用 data 的 TypeScript 等语言无法通过自动建议或静态检查的形式获得帮助。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-02-10
    • 2018-03-25
    • 2019-08-13
    • 2019-09-29
    • 2019-09-13
    • 2021-04-06
    相关资源
    最近更新 更多