У меня в приложении 2 гарда, AuthGuard и AccessGuard. AuthGuard защищает все страницы, как следует из названия, и сохраняет объект сеанса в GlobalService, а AccessGuard зависит от некоторых данных доступа в объекте сеанса, хранимом AuthGuard в GlobalService.
Проблема возникает, когда AuthGuard возвращает Observable, а затем одновременно AccessGuard выполняет проверку объекта сеанса, который еще не прибыл, и код ломается. Есть ли какой-либо другой способ ограничить выполнение AccessGuard до тех пор, пока не прибудет объект сеанса, или какой-либо другой способ обойти это состояние гонки?
#Примечание. Я не объединял логику AccessGuard с AuthGuard, так как только некоторые маршруты нужно проверять на наличие доступа, в то время как для всех остальных требуется аутентификация. Например, страница «Учетные записи» и страница «БД» доступны для всех, но для «Управления пользователями» и «Панели мониторинга» требуются внешние параметры доступа, которые исходят от объекта сеанса.
export const routes: Routes = [
{
path: 'login',
loadChildren: 'app/login/login.module#LoginModule',
},
{
path: 'logout',
loadChildren: 'app/logout/logout.module#LogoutModule',
},
{
path: 'forget',
loadChildren: 'app/forget/forget.module#ForgetModule',
},{
path: 'reset',
loadChildren: 'app/reset/reset.module#ResetModule',
},
path: 'pages',
component: Pages,
children: [
{ path: '', redirectTo: 'db', pathMatch: 'full' },
{ path: 'db', loadChildren: 'app/pages/db/db.module#DbModule' },
{ path: 'bi', loadChildren: 'app/pages/dashboard/dashboard.module#DashboardModule', canActivate:[AccessableGuard] },
{ path: 'account', loadChildren: 'app/pages/account/account.module#AccountModule' },
{ path: 'um', loadChildren: 'app/pages/um/um.module#UserManagementModule', canActivate:[AccessableGuard] },
],
canActivate: [AuthGuard]
}
];
export const routing: ModuleWithProviders = RouterModule.forChild(routes);
#EDIT: добавление защитных кодов
Защита авторизации:
canActivate(route:ActivatedRouteSnapshot, state: RouterStateSnapshot): Observable<boolean> | boolean{
return new Observable<boolean>( observer => {
this._dataService.callRestful('POST', params.SERVER.AUTH_URL + urls.AUTH.GET_SESSION).subscribe(
(accessData) => {
if (accessData['successful']) {
observer.next(true);
observer.complete();
console.log("done");
}
else {
observer.next(false);
observer.complete();
}
});
});
}
Доступная защита:
canActivate(route:ActivatedRouteSnapshot, state: RouterStateSnapshot): Observable<boolean> | boolean{
if(this._dataService.getModulePermission(route.routeConfig.path.toUpperCase()) < 2){
return false;
}
return true;
}
#ПРИМЕЧАНИЕ: _dataService — это GlobalService, в котором хранятся разрешения на доступ от AuthGuard.