简体   繁体   English

当页面重新加载时,firebase.auth.currentUser 返回 null

[英]When the page is reloaded, firebase.auth.currentUser returns null

I'm trying to implement a firebase authentication to my web app with react.我正在尝试通过 React 对我的 web 应用程序实施 firebase 身份验证。

The log-in/out flow is like this.登录/退出流程是这样的。

  • The user who succeeded in sign-in at the SIGN-IN page, redirected to the HOME page.在 SIGN-IN 页面成功登录的用户被重定向到 HOME 页面。

  • When Non-authenticated user access to the HOME page, redirected to the SIGN-IN page非认证用户访问HOME页面时,重定向到SIGN-IN页面

It is confirmed that the user is redirected to the HOME page from SIGN-IN and the user who clicked "sign out" button at the HOME page is redirected to the SIGN-IN page.确认用户从 SIGN-IN 被重定向到 HOME 页面,并且在 HOME 页面单击“退出”按钮的用户被重定向到 SIGN-IN 页面。

However, the problem is when the authenticated user reloads the page at the HOME page, the user is redirected to the SIGN-IN page and then redirected to the HOME page.但是,问题是当经过身份验证的用户在 HOME 页面重新加载页面时,用户将被重定向到 SIGN-IN 页面,然后再被重定向到 HOME 页面。

I supposed than the authenticated user isn't redirected to the SIGN-IN page.我认为经过身份验证的用户不会被重定向到登录页面。

How can I fix this problem?我该如何解决这个问题?

My codes are following:我的代码如下:

  • FirebaseContext.tsx FirebaseContext.tsx
import * as React from "react";
import { createContext, useContext } from "react";
import { firebase } from "../utils";

const FirebaseContext = createContext(firebase);

export const FirebaseProvider: React.FC = props => (
    <FirebaseContext.Provider value={firebase}>
        {props.children}
    </FirebaseContext.Provider>
);

export const useFirebase = () => useContext(FirebaseContext);

  • App.tsx应用程序.tsx
import * as React from "react";
import { Route, Switch } from "react-router-dom";
import * as routes from "./constants/routes";

import { FirebaseProvider } from "./contexts/FirebaseContext";
import { Home } from "./pages/Home";
import { SignIn } from "./pages/SignIn";

const App: React.FC = () => {
    return (
        <FirebaseProvider>
            <Switch>
                <Route exact={true} path={routes.SIGN_IN} component={SignIn} />
                <Route exact={true} path={routes.HOME} component={Home} />
            </Switch>
        </FirebaseProvider>
    );
};

export default App;
  • AuthUserHook.ts AuthUserHook.ts
import { useState, useEffect } from "react";
import { User } from "firebase";


export const useAuthUser = (firebase: any) => {
    const [authUser, setAuthUser] = useState<User | null>(firebase.auth.currentUser);
    useEffect(() => {
        const unsubcribe = firebase.auth.onAuthStateChanged((user: User | null) => setAuthUser(user));
        unsubcribe();
    }, []);

    return authUser;
};
  • SignIn.tsx登录.tsx
import * as React from "react";
import { useHistory } from "react-router-dom";

import { useFirebase } from "../../contexts/FirebaseContext";
import { useAuthUser } from "../../Hooks/AuthUserHook";
import * as routes from "../../constants/routes";
import { SignInForm } from "./SignInForm";


export const SignIn: React.FC = () => {
    const firebase = useFirebase();
    const authUser = useAuthUser(firebase);
    const history = useHistory();

    if (authUser) {
        history.push(routes.HOME);
    }

    return (
        <div>
            <h1>Sign in</h1>
            <SignInForm />
        </div>
    );
};
  • Home.tsx主页.tsx
import * as React from "react";
import { useHistory } from "react-router-dom";
import { useFirebase } from "../../contexts/FirebaseContext";
import { useAuthUser } from "../../Hooks/AuthUserHook";

import * as routes from "../../constants/routes";

export const Home: React.FC = () => {
    const firebase = useFirebase();
    const authUser = useAuthUser(firebase);
    const history = useHistory();

    if (!authUser) {
        history.push(routes.SIGN_IN);
    }

    return (
        <div>
            <h2>Home Page</h2>
            <p>The Home Page is accessible by every signed in user.</p>
        </div>
    );
};

Upon page load the Firebase SDK tries to restore the user's credentials from local storage.加载页面后,Firebase SDK 会尝试从本地存储恢复用户的凭据。 As part of this it checks with the server if the user's login session is still valid, and during that time the currentUser is null. Then once the login session is restored, it fires an onAuthStateChanged event with the new state. So you'll need to hook into that to update your state.作为其中的一部分,它会检查服务器是否用户的登录名 session 仍然有效,并且在此期间 currentUser 是 null。然后一旦登录名 session 恢复,它就会触发一个onAuthStateChanged事件,新的 state。所以你需要连接到它以更新您的 state。

The way I usually deal with this is to start on a "log in" screen and then redirect to the main screen when you get a valid user in your auth state change handler.我通常处理这个问题的方法是从“登录”屏幕开始,然后当您在 auth state 更改处理程序中获得有效用户时重定向到主屏幕。

One extra trick is to store your own flag in local storage when the user has authenticated before, and then read that when the page loads.一个额外的技巧是当用户之前已经过身份验证时将您自己的标志存储在本地存储中,然后在页面加载时读取它。 Since access to this local storage is synchronous, that means you can immediately show the main screen in cases where they've been signed in before.由于对该本地存储的访问是同步的,这意味着您可以在他们之前登录过的情况下立即显示主屏幕。 Just keep in mind that your local flag may be wrong (as that's precisely why Firebase has to check with the server), so you should be able to then handle navigating back to the login screen.请记住,您的本地标志可能是错误的(因为这正是 Firebase 必须与服务器核对的原因),因此您应该能够处理导航回登录屏幕。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 为什么 auth.currentUser 在 Firebase 的页面刷新上是 null - why auth.currentUser is null on page refresh in Firebase Authetication firebase currentUser 在页面重新加载时是 null - firebase currentUser is null on page reload (Firebase Web 持久性)登录后,currentUser 是 null,但是,在检查 auth object 后,它不是? - (Firebase Web Persistence) After sign in, currentUser is null, but, upon inspection of the auth object, it isn't? 如何使用 firebase_auth 包修复 flutter 应用程序中的 FirebaseAuth.instance.currentUser()? 它总是返回 null - How to fix FirebaseAuth.instance.currentUser() in flutter app using firebase_auth package? It is always returning null 如何在不请求的情况下在firebase-auth中首次加载时获取currentUser - How to get currentUser on first load in firebase-auth without requesting 使用会话/cookie 进行持久性时,如何在 Firebase 中设置“currentUser”? - How to set the `currentUser` in Firebase when using sessions/cookies for persistence? auth.currentUser.updateProfile 不是 function - auth.currentUser.updateProfile is not a function Flutter - Firebase Auth UID 在 Firestore 中注册为 Null - Flutter - Firebase Auth UID registers as Null in Firestore React Native Firebase Auth 用户是 null - React Native Firebase Auth user is null Firebase RTDB Unity - RunTransaction 总是返回 Null - Firebase RTDB Unity - RunTransaction Always Returns Null
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM