You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

为何页面刷新时React的App.js会渲染3次?

页面刷新时App.js的return语句执行3次的问题

页面首次登录加载时,App.js里的return语句执行2次符合预期,但刷新页面时会跑3次,搞不懂原因。下面是相关代码:

Index.js 代码

import React from "react";
import ReactDOM from "react-dom/client";
import { BrowserRouter } from "react-router-dom";

import "assets/plugins/nucleo/css/nucleo.css";
import "@fortawesome/fontawesome-free/css/all.min.css";
import "assets/scss/argon-dashboard-react.scss";

import { Auth0ProviderWithNavigate } from "./auth0-provider-with-navigate";
import { App } from "./app";
import store from "./app/store";
import { Provider } from "react-redux";

const root = ReactDOM.createRoot(document.getElementById("root"));

root.render(
  <BrowserRouter>
    <Auth0ProviderWithNavigate>
      <Provider store={store}>
        {console.log("Hit from Index")}
        <App />
      </Provider>
    </Auth0ProviderWithNavigate>
  </BrowserRouter>
);

App.js 代码

import { useAuth0 } from "@auth0/auth0-react";
import React, { useEffect } from "react";
import { Route, Routes } from "react-router-dom";
import { AuthenticationGuard } from "./components/authentication-guard";
import Admin from "layouts/Admin.js";
import Auth from "layouts/Auth.js";

export const App = () => {
  const { isLoading } = useAuth0();

  useEffect(() => {
    console.log("Hit from App UseEffect");
  }, []);

  return (
    <>
      {console.log("Hit from App Return", isLoading)}
      {isLoading ? (
        <div className="page-layout">
          <Auth />
        </div>
      ) : (
        <Routes>
          <Route path="/" element={<Auth />} exact />
          <Route path="/auth/*" element={<Auth />} />
          <Route
            path="/admin/*"
            element={<AuthenticationGuard component={Admin} />}
          />
        </Routes>
      )}
    </>
  );
};

问题原因和解决办法

为啥会多执行一次?

  1. React严格模式的影响:如果你的项目是Create React App这类默认开启严格模式的,开发环境下React会额外渲染一次组件,用来检测代码里的副作用问题。这会让return里的console.log多触发一次,刷新时就从2次变3次。
  2. Auth0状态变化触发重渲染:刷新页面时,Auth0的isLoading会从true切换为false,触发一次重渲染;加上严格模式的额外渲染,刚好三次。首次登录时因为Auth0可能缓存了状态,状态变化次数更少,所以只执行2次。
  3. 外层Provider的初始化重渲染:Auth0ProviderWithNavigate或Redux的Provider在刷新时会初始化内部状态,间接导致App组件重新渲染。

怎么处理?

  • 确认严格模式:看看Index.js里有没有<React.StrictMode>包裹,开发环境下的双重渲染是正常调试机制,生产环境会自动关闭,无需担心。
  • 调整日志位置:别在return里放console.log,因为return里的代码每次渲染都会执行。把日志移到useEffect里,按状态变化触发:
    useEffect(() => {
      console.log("App渲染完成,isLoading状态:", isLoading);
    }, [isLoading]); // 只有isLoading变化时才打印日志
    
  • 优化组件渲染逻辑:可以结合isAuthenticated和isLoading减少不必要的分支判断,或者用React.memo包裹App组件(不过因为依赖Auth0状态,memo的优化效果可能有限)。

总结

开发环境下的严格模式是额外渲染的主要原因,属于React的调试特性,生产环境不会有这个问题。如果嫌日志干扰,调整日志的放置位置即可,不要直接写在return语句中。

内容的提问来源于stack exchange,提问作者Noki

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.02 02:06:09