如何让 angular 路由守卫或它调用的服务在评估布尔值之前等待响应?
How can I get an angular route guard, or the service it calls, to wait for a response before evaluating the boolean?
我正在尝试在路由守卫中实现一些基本逻辑,以验证用户是否有权访问 URL。
当用户点击列表中的 link 时,我会获取 firestore 文档 ID 并将该 ID 作为 URL 参数传递到下一页。使用此方法,URL 会显示文档 ID,因此用户可以将 ID 更改为他们无权访问的内容。
我写的路由守卫工作...主要是。不幸的是,路由守卫第一次失败并把你踢回主页,但如果你重新登录,它就会起作用。设置一些断点和调试后,我可以看出评估 ID 和 returns 布尔值的代码没有等待文档用户 ID 的数据库调用。
我假设我需要实现某种 observable,但我不确定我应该在流程的哪个点发出 observable,以及我应该在哪里订阅(服务,还是守卫?)。我开始假设我应该在服务中进行一些调用,但也许将它们放在守卫本身会更好?
感谢您的帮助。
路由守卫
canActivate(route: ActivatedRouteSnapshot): boolean {
this.pid = route.paramMap.get('pid')
if (this.authService.isPartyAuth(this.pid) !== true) {
this.router.navigate(['home'])
}
return true;
}
授权服务
liveUid 正在构造函数中设置,以及 partyCollectionRef
isPartyAuth(pid: string) {
this.partyCollectionRef.doc(pid).ref.get().then((doc) => {
if (doc.exists) {
this.partyUserId = doc.data().uid
} else {
console.log("No such document!");
}
}).catch(function (error) {
console.log("Error getting document:", error);
});
return this.partyUserId == this.liveUid && this.partyUserId !== undefined && this.liveUid !== undefined ? true : false;
}
你不能return订阅任何东西,改用地图,你还需要添加一个return声明。
canActivate() {
// add 'return'
return this.authService.isPartyAuth(this.pid)
// change this!
// .subscribe(resp=> {
.map(resp=> {
if(!resp) {
this.router.navigate(['home'])
return false;
}
return true;
});
}
我进行了一些小调整并使它正常工作:
路由守卫
我将整个函数设为异步,并在对服务的调用中添加了等待。
async canActivate(route: ActivatedRouteSnapshot): Promise<boolean> {
this.pid = route.paramMap.get('pid')
if (await this.authService.isPartyAuth(this.pid) !== true) {
this.router.navigate(['home'])
}
return true;
}
}
授权服务
我也更新了auth服务到return我等待后的boolean,得到了文档数据
isPartyAuth(pid: string) {
return this.partyCollectionRef.doc(pid).ref.get().then((doc) => {
if (doc.exists) {
this.partyUserId = doc.data().uid
return this.partyUserId == this.liveUid && this.partyUserId !== undefined && this.liveUid !== undefined ? true : false;
} else {
console.log("No such document!");
return false
}
}).catch(function (error) {
console.log("Error getting document:", error);
});
}
我正在尝试在路由守卫中实现一些基本逻辑,以验证用户是否有权访问 URL。
当用户点击列表中的 link 时,我会获取 firestore 文档 ID 并将该 ID 作为 URL 参数传递到下一页。使用此方法,URL 会显示文档 ID,因此用户可以将 ID 更改为他们无权访问的内容。
我写的路由守卫工作...主要是。不幸的是,路由守卫第一次失败并把你踢回主页,但如果你重新登录,它就会起作用。设置一些断点和调试后,我可以看出评估 ID 和 returns 布尔值的代码没有等待文档用户 ID 的数据库调用。
我假设我需要实现某种 observable,但我不确定我应该在流程的哪个点发出 observable,以及我应该在哪里订阅(服务,还是守卫?)。我开始假设我应该在服务中进行一些调用,但也许将它们放在守卫本身会更好? 感谢您的帮助。
路由守卫
canActivate(route: ActivatedRouteSnapshot): boolean {
this.pid = route.paramMap.get('pid')
if (this.authService.isPartyAuth(this.pid) !== true) {
this.router.navigate(['home'])
}
return true;
}
授权服务
liveUid 正在构造函数中设置,以及 partyCollectionRef
isPartyAuth(pid: string) {
this.partyCollectionRef.doc(pid).ref.get().then((doc) => {
if (doc.exists) {
this.partyUserId = doc.data().uid
} else {
console.log("No such document!");
}
}).catch(function (error) {
console.log("Error getting document:", error);
});
return this.partyUserId == this.liveUid && this.partyUserId !== undefined && this.liveUid !== undefined ? true : false;
}
你不能return订阅任何东西,改用地图,你还需要添加一个return声明。
canActivate() {
// add 'return'
return this.authService.isPartyAuth(this.pid)
// change this!
// .subscribe(resp=> {
.map(resp=> {
if(!resp) {
this.router.navigate(['home'])
return false;
}
return true;
});
}
我进行了一些小调整并使它正常工作:
路由守卫
我将整个函数设为异步,并在对服务的调用中添加了等待。
async canActivate(route: ActivatedRouteSnapshot): Promise<boolean> {
this.pid = route.paramMap.get('pid')
if (await this.authService.isPartyAuth(this.pid) !== true) {
this.router.navigate(['home'])
}
return true;
}
}
授权服务
我也更新了auth服务到return我等待后的boolean,得到了文档数据
isPartyAuth(pid: string) {
return this.partyCollectionRef.doc(pid).ref.get().then((doc) => {
if (doc.exists) {
this.partyUserId = doc.data().uid
return this.partyUserId == this.liveUid && this.partyUserId !== undefined && this.liveUid !== undefined ? true : false;
} else {
console.log("No such document!");
return false
}
}).catch(function (error) {
console.log("Error getting document:", error);
});
}