當前用戶的 Console.logs
我有一個 UserContext.js 檔案,其中包含所有 useContext 掛鉤。顯示一些用戶資訊和“登錄”或“退出”按鈕的 Nav.js。顯示用戶資訊的 Profile.js。包含組件和 useContext 的 App.js。
發生的事情是,如果我與用戶一起登錄,一切都會顯示出來,我可以導航到各個頁面并且用戶資訊保持顯示。如果我從導航選單中單擊注銷,所有用戶資訊而不是顯示“無用戶資訊”會在所有頁面上顯示空欄位。“退出”按鈕再次出現。我認為這是因為每次我導航到不同頁面時,將我所有組件包裝在 App.js 中的 UserContextProvider 都會從 toggleUser 函式呼叫 auth.signout ?我可以從 UserContextProvider 的范圍中提取 toggleUser 函式嗎?還是有其他事情發生?
應用程式.js
import './App.css';
import 'bootstrap/dist/css/bootstrap.min.css';
import React from "react";
import { BrowserRouter, Routes, Route } from 'react-router-dom';
import { UserContextProvider } from '../../../src/util/Context/UserContext'
import Navmenu from '../Nav/Nav';
import Home from '../../Pages/Home/Home';
import Signin from '../../Pages/Sign-in/Sign-in';
import Signup from '../../Pages/Sign-up/Sign-up';
import Profile from '../../Pages/Profile/Profile';
import Footer from '../Footer/Footer';
const App = () => {
return (
<div className="App">
<BrowserRouter>
<UserContextProvider>
<Navmenu />
<hr className="p-0 m-0"></hr>
<Routes>
<Route exact path='/' element={<Home />} />
<Route path='/signin' element={<Signin />} />
<Route path='/signup' element={<Signup />} />
<Route path='/profile' element={<Profile />} />
</Routes>
<Footer />
</UserContextProvider>
</BrowserRouter>
</div>
)
};
export default App;
用戶背景關系.js
import React, { useContext, useState, useEffect } from 'react';
import { auth, createUserProfileDocument } from "../firebase/firebase.utils";
const UserContext = React.createContext(null);
const UserUpdateContext = React.createContext();
export const useUserContext = () => {
// useContext hook
return useContext(UserContext);
}
export const useUserContextUpdate = () => {
// useContext hook
return useContext(UserUpdateContext)
}
export const UserContextProvider = ({ children }) => {
const [currentUser, setUser] = useState(null);
let unsubscribeFromAuth = null;
useEffect(() => {
unsubscribeFromAuth = auth.onAuthStateChanged(async userAuth => {
if (userAuth) {
const userRef = await createUserProfileDocument(userAuth);
userRef.onSnapshot(snapShot => {
setUser({
id: snapShot.id,
...snapShot.data()
});
});
} else {
setUser({ currentUser: userAuth })
}
});
return () => {
unsubscribeFromAuth();
};
}, [])
const toggleUser = () => {
auth.signOut()
.then((currentUser) => {
setUser(null)
})
.catch(e => console.log('There was a error:'(e)))
}
return (
<UserContext.Provider value={currentUser} >
<UserUpdateContext.Provider value={toggleUser} >
{children}
</UserUpdateContext.Provider >
</UserContext.Provider >
)
};
導航.js
import React from 'react';
import { Link } from 'react-router-dom';
import './Nav.css';
import { useUserContext, useUserContextUpdate } from '../../../src/util/Context/UserContext';
import { auth } from '../../util/firebase/firebase.utils';
import { Nav, Navbar, NavDropdown } from 'react-bootstrap';
import Bell from './img/Bell.svg';
import Message from './img/Message.svg';
import Userprofile from './img/Userprofile.svg';
import Aboutme from './img/Aboutme.svg';
import Findfriends from './img/Findfriends.svg';
import Accountsetting from './img/Accountsetting.svg';
const Navmenu = ({ }) => {
const currentUser = useUserContext();
const toggleUser = useUserContextUpdate();
return (
<div className='tc f3'>
<Navbar bg='light' expand='lg'>
<a className="text-decoration-none" href="/">
<Navbar.Brand className="mx-2 mx-lg-5">Yelp-Clone</Navbar.Brand>
</a>
<Navbar.Toggle aria-controls="basic-navbar-nav" />
<Navbar.Collapse id="basic-navbar-nav">
<hr></hr>
<Nav className='ml-5'>
<Nav.Link className='link-font' href="#home">Write a Review</Nav.Link>
<Nav.Link className='link-font' href="#link">Events</Nav.Link>
<Nav.Link className='link-font' href="#link">Talk</Nav.Link>
</Nav>
<div className="d-flex flex-row justify-content-lg-center align-items-center ml-auto">
<img className='nav-img me-2' src={Message}></img>
<img className='nav-img me-2' src={Bell}></img>
<img className='nav-img-lrg' src={Userprofile}></img>
<NavDropdown className='custom-dropdown-class me-3' id="basic-nav-dropdown">
<div className="d-flex flex-row">
<img className='nav-img-sml me-2' src={Userprofile}></img>
<div className="d-flex flex-column">
{
currentUser ?
<span>{currentUser.displayName}</span>
:
<span>No User Found</span>
}
{
currentUser ?
<span>{currentUser.email}</span>
:
<span>No Email Found</span>
}
</div>
</div>
<NavDropdown.Divider />
<div className="link-wrapper my-1">
<img className="link-font-sml me-2 inline-block" src={Aboutme}></img><a className="link-font-sml"><Link className="link-font-sml" to="/profile">About Me</Link></a>
</div>
<div className="link-wrapper my-1">
<img className="link-font-sml me-2 inline-block" src={Findfriends}></img><span className="link-font-sml">Find Friends</span>
</div>
<div className="link-wrapper my-1">
<img className="link-font-sml me-2 inline-block" src={Accountsetting}></img><span className="link-font-sml">Account Settings</span>
</div>
<NavDropdown.Divider />
<NavDropdown.Item className="p-0">
<div className="text-center options">
{
currentUser ?
<a className="option" onClick={toggleUser}>
Sign Out
</a>
:
<a><Link className="option" to="/signin">Sign In</Link></a>
}
</div>
</NavDropdown.Item>
</NavDropdown>
</div>
</Navbar.Collapse>
</Navbar>
</div>
)
}
export default Navmenu
uj5u.com熱心網友回復:
如果我不得不冒險猜測為什么用戶不保持“注銷”狀態,那是因為內部訂閱也useEffect沒有取消訂閱。它仍然可以更新user狀態。
currentUser當回呼中存在 falseyuserAuth值時,請確保您還將狀態重置為 null onAuthStateChanged。
useEffect(() => {
let unsubscribeFromAuth = null;
let unsubscribeFromSnapshot = null;
unsubscribeFromAuth = auth.onAuthStateChanged(async userAuth => {
if (userAuth) {
const userRef = await createUserProfileDocument(userAuth);
unsubscribeFromSnapshot = userRef.onSnapshot(snapShot => {
setUser({
id: snapShot.id,
...snapShot.data()
});
});
} else {
setUser(null); // <-- reset user state
}
});
return () => {
unsubscribeFromAuth();
unsubscribeFromSnapshot();
};
}, []);
轉載請註明出處,本文鏈接:https://www.uj5u.com/gongcheng/363621.html
