【发布时间】:2019-04-05 12:08:38
【问题描述】:
在从 React 类重构为 React 钩子时,我在弄清楚如何更改身份验证处理组件时遇到了一些麻烦。
这是我的类中的相关代码:
state = {
user: null
}
componentDidMount() {
authGetUser(user => {
if (user !== this.state.user) {
this.setState({user})
}
})
}
componentWillUnmount() {
authUnsubscribe()
}
handleAuthClick = () => {
if (this.state.user) {
authSignOut()
} else {
authSignIn()
}
}
这里是 钩子:
const [user, setUser] = useState<firebase.User | null>(null)
useEffect(() => {
return authUnsubscribe() // runs on mount and unmount only
}, [])
useEffect(() => {
authGetUser(usr => setUser(usr))
}, [])
const handleAuthClick = () => {
if (user) {
authSignOut()
} else {
authSignIn()
}
}
另外,这里是我的其他相关方法:
const authGetUser = (callback: (user: firebase.User | null) => void) => {
initFirebase()
authUnsubscribe()
userUnsubscribe = firebaseAuth.onAuthStateChanged(callback)
}
export const authUnsubscribe = () => {
if (userUnsubscribe) {
userUnsubscribe()
}
}
const authSignIn = () => {
googleAuth.signIn().then((googleUser: any) => {
var credential = firebase.auth.GoogleAuthProvider.credential(googleUser.getAuthResponse().id_token)
firebaseAuth.signInAndRetrieveDataWithCredential(credential)
})
}
const authSignOut = () => {
googleAuth
.signOut()
.then(firebaseAuth.signOut())
}
这两个例子都有效。但是,当我注销并使用 hooks 版本登录时,我在控制台中收到一条错误消息,提示
Warning: Can't perform a React state update on an unmounted component. This is a no-op, but it indicates a memory leak in your application. To fix, cancel all subscriptions and asynchronous tasks in the componentWillUnmount method.
这表明清理工作不正确。
是的,我知道我可以继续使用具有有效类的版本。但是我想通过解决这个问题来更好地理解 React 钩子。
有什么想法吗?
【问题讨论】:
-
您在第一个
useEffect中直接调用authUnsubscribe,但您想返回一个应在卸载时运行的函数。useEffect(() => authUnsubscribe, []) -
我尝试了你的建议。它仍然可以正常工作,包括控制台中的错误消息...
标签: reactjs firebase-authentication react-hooks