一个项目由 4 个来源组成。在这个项目中,我想将cookie重写到本地存储。我已经在用户源中实现了它,并且它正确保存在本地存储中。然而,在登陆源中,尽管进行了更改,我仍无法在本地存储中检索令牌。重要的一点是,当我登录用户时,它应该也会自动登录到登陆。下面,我附上了登陆源的文件。
main.js
import { useContext, createContext, useState, useEffect } from 'react'
// import { setCookie } from 'cookies-next'
import { useRouter } from 'next/router'
import { cookies } from 'next/headers'
import { useLogout } from '@/core/services/react-query/auth'
const context = createContext()
export const useMainContext = () => {
return useContext(context)
}
const MainContextProvider = ({
children,
theme: initialTheme,
token: _token,
}) => {
const [theme, _setTheme] = useState(initialTheme)
const [token, _setToken] = useState(_token)
const [isOpen, _setIsOpen] = useState(false)
const router = useRouter()
const { pathname, asPath, query, locale } = router
useEffect(() => {
const storedTokenFromCookies = document.cookie
.split('; ')
.find(row => row.startsWith('token='));
if (storedTokenFromCookies) {
const tokenValue = storedTokenFromCookies.split('=')[1];
setToken(tokenValue); // Set token in the state
localStorage.setItem('token', tokenValue); // Also set it in localStorage
console.log('User found in cookies:', tokenValue);
// Redirect user to profile page
router.push('/profile');
} else {
const storedToken = localStorage.getItem('token');
if (storedToken) {
setToken(storedToken); // Update state if the token exists in localStorage
}
}
}, [router]);
const toggleTheme = () => {
const value = theme === 'dark' ? 'light' : 'dark'
// setCookie('theme', value)
localStorage.setItem('theme', value)
_setTheme(value)
if (value === 'dark')
{document.documentElement.classList.add('dark')
}else {document.documentElement.classList.remove('dark')}
}
const toggleLang = () => {
const lang = locale === 'en' ? 'fa' : 'en'
router.push({ pathname, query }, asPath, { locale: lang })
document.documentElement.setAttribute(
'dir',
lang === 'en' ? 'ltr' : 'rtl'
)
// setCookie('lang', lang, { path: '/' })
localStorage.setItem('lang', lang)
}
const setToken = (value) => {
// setCookie('token', value)
localStorage.setItem('token', value)
_setToken(value)
}
const setIsOpen = () => {
_setIsOpen((prevState) => !prevState)
}
return (
<context.Provider
value={{
theme,
toggleTheme,
toggleLang,
token,
setToken,
setIsOpen,
isOpen,
}}>
{children}
</context.Provider>
)
}
export default MainContextProvider
_document.js
import Document, { Html, Head, Main, NextScript } from 'next/document'
import { ServerStyleSheet } from 'styled-components';
class MyDocument extends Document {
static async getInitialProps(ctx) {
const sheet = new ServerStyleSheet()
const originalRenderPage = ctx.renderPage
try {
// Run the React rendering logic synchronously
ctx.renderPage = () =>
originalRenderPage({
// Useful for wrapping the whole react tree
enhanceApp: (App) => (props) =>
sheet.collectStyles(<App {...props} />),
// Useful for wrapping in a per-page basis
enhanceComponent: (Component) => Component,
})
// Run the parent `getInitialProps`, it now includes the custom `renderPage`
const initialProps = await Document.getInitialProps(ctx)
const theme = ctx.req?.cookies?.theme || 'dark'
const lang = ctx.req?.cookies?.lang
const dir = lang === 'en' ? 'ltr' : 'rtl'
return {
...initialProps,
theme,
dir,
styles: [initialProps.styles, sheet.getStyleElement()]
}
}
finally {
sheet.seal()
} }
render() {
return (
<Html className={this.props.theme} dir={this.props.dir}>
<Head />
<body>
<Main />
<NextScript />
</body>
</Html>
)}}
export default MyDocument
_app.js
import '@/styles/globals.css'
import Providers from '@/components/layout/Providers'
import { getCookie, setCookie } from 'cookies-next'
import MainLayout from '@/components/layout/main/MainLayout'
import { GlobalStyles } from '@/styles/styled/GlobalStyle.styled'
export default function App({ Component, pageProps, theme, ...rest }) {
// TODO: if cookie is empty
let _theme = theme
if (!_theme) {
_theme = 'dark'
setCookie('theme', _theme)
}
return (
<Providers theme={_theme} {...rest}>
<MainLayout pageProps={pageProps}>
<GlobalStyles />
<Component {...pageProps} />
</MainLayout>
</Providers>
)
}
App.getInitialProps = ({ ctx }) => {
const theme = getCookie('theme', ctx)
const token = getCookie('token', ctx)
return {
theme,
token,
}
}
考虑到登录应该在登陆页面渲染时完成,如何将cookie重写到本地存储?
我在这里看到一个设计问题。 Session是为了让用户可以访问api。 对于任何与 UI 相关的东西,你都有状态。 不要试图通过会议,而是尝试从以下方面思考:
isLoggedIn
,如果为 false,则重定向用户登录)