Метод защиты маршрута, нарушающий маршрутизацию - PullRequest
0 голосов
/ 30 августа 2018

Редактировать: StackBlitz минимальное воспроизведение , кажется, работает, так что есть что-то еще не так, как кажется ..

Угловой 6.1.3

У меня есть маршрут, который нужно охранять, основываясь на параметре slug.

{
  path: 'market/:slug',
  component: MarketComponent,
  canActivate: [RoleGuard],
},

RoleGuard canActivate метод:

canActivate(route: ActivatedRouteSnapshot): Observable<boolean> | Promise<boolean> | boolean {
  const market$ = this.marketService.getBySlug(
    route.paramMap.get('slug')
  ); // returns an observable of the corresponding market object

  // Verify the user is authorized to see this market.
  return this.authService.isAuthorized(market);
}

authService.isAuthorized:

isAuthorized(market: Observable<Market>): Observable<boolean> {
  return combineLatest(this.user$, market).pipe(
    map(([user, market]) => {
      // Check roles of the user based on the market's configuration
      return true;
    })
  );
}

Я удалил логику пользователя / рынка, просто пытаясь убрать все, что может вызывать проблемы, но когда я возвращаю описанный выше метод внутрь canActivate, маршрутизация останавливается. Трасса трассы:

Router Event: NavigationStart
NavigationStart(id: 2, url: '/market/sams-corner-store')
NavigationStart {id: 2, url: "/market/sams-corner-store", navigationTrigger: "imperative", restoredState: null}

Router Event: RoutesRecognized
RoutesRecognized(id: 2, url: '/market/sams-corner-store', urlAfterRedirects: '/market/sams-corner-store', state: Route(url:'', path:'') { Route(url:'market/sams-corner-store', path:'market/:slug') } )
RoutesRecognized {id: 2, url: "/market/sams-corner-store", urlAfterRedirects: "/market/sams-corner-store", state: RouterStateSnapshot}

Router Event: GuardsCheckStart
GuardsCheckStart(id: 2, url: '/market/sams-corner-store', urlAfterRedirects: '/market/sams-corner-store', state: Route(url:'', path:'') { Route(url:'market/sams-corner-store', path:'market/:slug') } )
GuardsCheckStart {id: 2, url: "/market/sams-corner-store", urlAfterRedirects: "/market/sams-corner-store", state: RouterStateSnapshot}

Router Event: ChildActivationStart
ChildActivationStart(path: '')
ChildActivationStart {snapshot: ActivatedRouteSnapshot}

Router Event: ActivationStart
ActivationStart(path: 'market/:slug')
ActivationStart {snapshot: ActivatedRouteSnapshot}

Во время обычной маршрутизации запускаются другие события Маршрутизатора, но здесь он просто останавливается. Я думаю, это как-то связано с тем, что isAuthorized ничего не излучает, но я в тупике. После сбоя навигация в любом месте ничего не делает; URL-адрес остается прежним, и на консоли ничего не регистрируется.

Иногда метод даже не вызывается, console.log не вызывается в combineLatest / withLatestFrom.

Я пробовал combineLatest и withLatestFrom с некоторыми вариантами операторов, но безрезультатно.

Ответы [ 2 ]

0 голосов
/ 30 августа 2018

canActivate guard будет подписываться на возвращаемое Observable и ждать, пока это Observable будет завершено, до того момента никакое другое событие маршрутизатора не будет обработано.
Добавьте first() (Rx operator) к пользователю $ и market $ Observable.
PS вместо combineLatest используйте forkJoin.

0 голосов
/ 30 августа 2018

Вы делаете это правильно, но охранник требует, чтобы наблюдаемое завершилось. Так что вы застряли в ожидании этого.

попробуйте сделать

return this.authService.isAuthorized(market).pipe(
    take(1)
);

это займет первый результат и завершится, что должно решить вашу проблему.

...