我正在使用带有Firebase身份验证的angular。 当我使用onAuthStateChanged方法知道用户是否登录时,它不会返回用户 甚至当我想检索用户数据时甚至使用angularfireAuth.currentUser也给我这个错误: 例如,我在查询函数中使用了afAuth.currentUser.uid
未捕获(承诺):TypeError:无法读取null的属性“ uid”
这是我在authService的构造函数中调用的代码:
firebase.auth().onAuthStateChanged(firebaseUser => {
if (firebaseUser) {
console.log(firebaseUser.uid)
this.user.next(firebaseUser)
return (firebaseUser.uid)
} else {
return (null)
}
})
我认为我必须异步执行此操作,但是我不知道该怎么办? 有任何想法吗?
答案 0 :(得分:1)
由于您使用的是angularfire,因此建议您听authState
。我看到您正在调用next
,因此正在公开某种可观察的主题。但是我会将authState
中的值分配给一个Observable,您可以订阅该Observable以获取实时更改,因为只要authState
发生更改,就会触发该更改。
服务:
import { User } from 'firebase';
// ...
user$: Observable<User | null>;
constructor(
private afAuth: AngularFireAuth
) {
this.user$ = this.afAuth.authState;
}
然后您可以在组件中订阅user$
:
this.myService.user$.subscribe(....)
在这里,您需要记住在组件被销毁时退订!!
您还可以在服务中编写一个函数,该函数可以返回一次用户,而您不必担心取消订阅。
使用与上面相同的代码,但添加:
getUser() {
return this.user$.pipe(first())
}
现在,当您在组件中订阅此功能时,您的用户只会被发出一次。
如果您需要在其他依赖于uid
的异步功能中使用此用户,则可以使用switchMap
或mergeMap
链接这些请求。所以你可以做的是...
this.myService.getUser().pipe(
switchMap((user: User) => {
return this.getCat(user.uid)
})
// will console true or false
).subscribe(data => console.log(data))
答案 1 :(得分:0)
您是否将代码包装到函数中并在页面加载时调用该函数?也许尝试将其包装在函数中,并在页面首次加载时调用loginStatus函数
function loginStatus() {
firebase.auth().onAuthStateChanged(firebaseUser => {
if (firebaseUser) {
console.log(firebaseUser.uid)
this.user.next(firebaseUser)
return (firebaseUser.uid)
} else {
return (null)
}
})
}