我试图找到一种方法来router-outlet
根据用户的角色有条件地渲染子路由中的组件。
例如,我有一个 DashboardComponent,其中包含一个router-outlet
. 我希望在 child 中呈现的组件router-outlet
根据用户角色而有所不同,该角色由令牌传入,而无需指定其他路由。
我希望尝试在接近此的地方编写我的路线:
{
path: 'dashboard',
component: DashboardComponent,
children: [
{ path: '', component: DataViewsComponent }, // For standard user role
{ path: '', component: AdminViewsComponent } // For the admin user role
]
}
这种确切的模式当然行不通,因为路由器只看到两条相同的路由路径。
我设法编写了一个服务,该服务使用该canActivate
属性来检查用户的角色并根据角色转发到不同的路由:
@Injectable()
export class RoleRouteRedirectService implements CanActivate {
roleRoutingPermissions: any = {
// Will contain redirects for every route in the app
// For this example, only contains reroutes for the dashboard route
['dashboard']: [
{ roles: [ 'user' ], redirect: '/dashboard/admin' },
{ roles: [ 'admin' ], redirect: '/dashboard/admin' }
]
};
constructor(private router: Router) {}
canActivate(route: ActivatedRouteSnapshot): boolean {
// In the larger app, the roles are taken out of the token
// Here I've mocked them from localStorage for ease
const userRoles: string[] = localStorage.getItem('user-role').split(',');
const url: string = route.data.url;
// Find the object property matching the desired origin URL
if (url in this.roleRoutingPermissions) {
// Iterate over the array of route permissions in this property
for (const item of roleRoutingPermissions[url]) {
// If we find the entry for the role, apply the redirect
if (item.roles.some(role => userRoles.includes(role))) {
this.router.navigate([ item.redirect ]);
return false;
}
}
}
// Otherwise, fail
console.log('Could not find matching route permissions');
return false;
}
}
这将采用不同的 Routes 模式:
{
path: 'dashboard',
component: DashboardComponent,
canActivate: [ RoleRouteRedirectService ],
data: {
url: 'dashboard'
},
// Conditional Routes
children: [
{
path: 'user',
component: DataViewsComponent,
},
{
path: 'admin',
component: AdminHomeComponent,
}
]
}
现在,这真的很好用。但是,我对这种模式有以下问题:
- 我想避免有额外的路线 - 即我不想要
dashboard/user
,我只想dashboard
为不同的用户呈现不同的孩子 - 我可以看到这将很快导致我的路线,并且 RoleRouteRedirectService 随着应用程序的增长变得非常复杂
- 这感觉不是使用路由保护的正确方法(如果我错了,请纠正我!)
- 我觉得必须有一种方法可以从我缺少的路由器内部处理这个问题
如果有人有任何想法,我很想听听他们的意见。我很欣赏这是一个相对复杂的问题 - 如果我错过了任何有用的信息,请发表评论,我会看看可以添加什么。