【发布时间】:2017-12-28 13:45:07
【问题描述】:
在每次请求之前,我都想确保有可用的用户配置文件。我使用 canActivateChild 守卫来执行此操作。
根据 angular2 的文档,可以返回一个 observable:https://angular.io/api/router/CanActivateChild
app.routes.ts
export const routes: Routes = [
{
path: '',
canActivateChild: [ProfileGuard],
children: [
{
path: 'home',
component: HomeComponent,
canActivate: [AuthGuard]
},
{
path: 'login',
component: LoginComponent,
canActivate: [GuestGuard]
},
}
];
canActivatedChild在子路由canActivate之前执行
profile.guard.ts:
export class ProfileGuard implements CanActivateChild {
constructor(private profileService: ProfileService, private snackbar: MdSnackBar) { }
canActivateChild(childRoute: ActivatedRouteSnapshot, state: RouterStateSnapshot): boolean | Observable<boolean> {
if (this.profileService.user == null && localStorage.getItem('__token') != null) {
return this.profileService.loadProfile().map((user) => {
console.log('profile loaded');
this.profileService.user = <UserModel>user.data;
return true;
});
}
return true;
}
}
加载配置文件功能:
public loadProfile(): Observable<any> {
console.log('load');
return this.http.get('/profile').map(res => res.json());
}
当我浏览菜单(<a> 和 routeLink)时,console.log('profile loaded') 有效。但是如果我用 f5 或通过浏览器重新加载页面,它永远不会到达那里..
console.log('load') 总是被执行。
编辑:
如果我在canActivateChild返回:
return Observable.of(true).map(() => {
console.log('Test');
return true;
});
它工作正常...我得到console.log('test')
【问题讨论】:
-
在 F12 浏览器控制台的网络选项卡上,看到对 /profile 的请求了吗,是否成功?
-
这是一个有趣的问题。如果您只返回
Observable.of(true)而不是调用this.profileService.loadProfile(),事情会按预期工作吗? -
如果可能的话,你能不能试试 plnkr ,那样你会很快得到帮助。您可以将虚拟数据用于 HTTP 调用
-
@HendrikBrummermann 是的,请求已经发出,并且使用正确的数据也成功
-
如果你在
canActivateChild()内部console.log(而不是在 Observable 链本身),它可以工作吗?
标签: angular angular2-routing observable angular2-observables angular2-guards