[英]Angular Route Guard based on collection query result
I have a 'Teams' collection in Firestore.我在 Firestore 中有一个“团队”系列。 A team document will include a team_users
map field where userID: true
if they are a part of that team.团队文档将包含一个team_users
map 字段,其中userID: true
如果他们是该团队的一部分。
I have a query in a service that returns and displays all team documents where the logged in user id matches an ID within the team_users
field.我在服务中有一个查询,该查询返回并显示所有团队文档,其中登录的用户 ID 与team_users
字段中的 ID 匹配。
getTeamsList(user_id: string) {
this.teamsCollection = this.afs.collection<any>(`teams`, ref => ref.where(`team_users.${user_id}`, "==", true))
this.teams = this.teamsCollection.snapshotChanges().pipe(
map(actions => actions.map(a => {
const data = a.payload.doc.data();
const id = a.payload.doc.id;
return { id, ...data };
}))
).pipe(shareReplay());
}
What I need to achieve is a route guard that performs the following:我需要实现的是执行以下操作的路由守卫:
Team A
, but have since left, they should not be able to access this route and should instead be redirected back to the url of /teams
例如,如果用户在Team A
中时有一个文档书签,但后来离开了,他们应该无法访问此路由,而是应该重定向回/teams
的 url/teams
listing url如果用户不属于任何团队(集合查询不产生任何结果),则无法访问/teams
列表 url 中的一部分Note: A user can be a part of multiple teams.注意:一个用户可以是多个团队的一部分。 If the user was a part of Team A, B and C and has bookmarks for pages in Team A, but has since left, the route guard should prevent them from accessing any pages that were a part of Team A, but still allow access to Team B and C pages.如果用户是团队 A、B 和 C 的成员,并且在团队 A 中有页面的书签,但后来离开了,则路由守卫应阻止他们访问属于团队 A 的任何页面,但仍允许访问B 组和 C 页面。
Does this mean that:这是否意味着:
Any help would be greatly appreciated.任何帮助将不胜感激。
A user is on /teams page displaying teams (You don't need a guard on this route).用户在 /teams 页面上显示团队(您不需要在这条路线上看守)。 When a user clicks on one of the teams navigate to /teams/teamID (Now this route needs a guard to prevent a user that doesn't belong to teamID from accessing it. To set the guard do this:当用户点击其中一个团队时,导航到 /teams/teamID (现在这条路线需要一个守卫来防止不属于 teamID 的用户访问它。要设置守卫,请执行以下操作:
isTeamMember(userId: string, teamId: string): Observable < Boolean > { return this.firestore.doc < any > (`teams/${teamId}`).snapshotChanges().pipe( map(value => value.payload.data().team_users[userId] === true)); }
canActivate( next: ActivatedRouteSnapshot, state: RouterStateSnapshot): Observable < boolean > | Promise < boolean > | boolean { return this.firestoreService.isTeamMember(userIdFromWhereYouStoreYourCurrentUser, teamIdFromTheCurrentUrl).pipe(map(isTeamMember => { if (isTeamMember) { return true; } else { //Add your not team member logic here, eg Stay in the current route, may be show an error message return false; } }), take(1)); }
You can do it this way: 1. Make an Auth guard, let say it "AG".你可以这样做: 1. 做一个 Auth 守卫,假设它是“AG”。 2. In this "AG", make a REST call to your backend. 2. 在此“AG”中,对您的后端进行 REST 调用。 Sending the bookmark ID, USer ID, Current Team Id.发送书签 ID、用户 ID、当前团队 ID。 "AG" will get triggered on route change where-ever applied. “AG”将在任何应用的路线更改时触发。 3. This REST call will compare the current team Id and the Team Id saved with that Bookmark(Assumption: Bookmark table has the column of Team Id as foreign key). 3. 这个 REST 调用将比较当前团队 ID 和使用该书签保存的团队 ID(假设:书签表有团队 ID 列作为外键)。 4. So when the service return TRUE/FALSE, then "AG" will know that if it is authorized or not. 4.所以当服务返回TRUE/FALSE时,“AG”就会知道它是否被授权。 5. If it is FALSE, then route user to whatever url. 5. 如果为 FALSE,则将用户路由到 url。
Example of sample code:示例代码示例:
@Injectable()
export class AuthGuardService implements CanActivate
{
constructor(public auth: AuthService, public router: Router) {}
canActivate(): boolean
{
if (!this.auth.isAuthenticated()) {
this.router.navigate(['team']);
return false;
}
return true;
}
}
Adding the route example:添加路由示例:
export const ROUTES: Routes = [
{ path: '', component: Home},
{
path: 'team/{id}',
component: TeamComponent,
canActivate: [AuthGuard]
},
{ path: '**', redirectTo: '' }
];
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.