Next.js项目构建后_app chunk体积过大,如何优化?
问题描述
我通过create-next-app创建了一个Next.js项目,并将_app.ts修改为如下代码:
import "../../public/assets/css/bootstrap.css"; import "antd/dist/antd.css"; import "../../public/assets/css/common.css"; import "../styles/globals.css"; import "../styles/builderGlobals.css"; import "../../public/assets/css/quiz.css"; import "../../public/assets/css/main.css"; import "../../public/assets/css/responsive.css"; import Head from "next/head"; import { wrapper } from "../app/store"; import { setUser } from "../Modules/Auth/authSlice"; import Layout from "../components/Layouts/layout"; import type { AppPropsWithLayout } from "../utils/types"; import { setNotifSettingsData } from "../Modules/Notifications/notificationsSlice"; import serverApi from "../utils/axios/serverApi"; import NextNProgress from "nextjs-progressbar"; import { useAppSelector } from "../app/hooks"; const MyApp = ({ Component, pageProps }: AppPropsWithLayout) => { const favicon = useAppSelector(state => state.settingsData.favico_icon); const getLayout = Component.getLayout ?? ((page) => ( <Layout> <Head> <link rel="shortcut icon" href={favicon || "/img/favicon.png"} /> </Head> <NextNProgress /> {page} </Layout> )); return getLayout(<Component {...pageProps} />); }; MyApp.getInitialProps = wrapper.getInitialAppProps( (store) => async ({ Component, ctx }) => { if (!ctx.req) { return { pageProps: { ...(Component.getInitialProps ? await Component.getInitialProps({ ...ctx, store }) : {}), pathname: ctx.pathname, }, }; } try { const { data: initialData } = await serverApi( ctx, `/settings/get-initial-site-data` ); store.dispatch(setUser(initialData?.authUser)); store.dispatch(setNotifSettingsData(initialData?.siteSettings)); return { pageProps: { ...(Component.getInitialProps ? await Component.getInitialProps({ ...ctx, store }) : {}), pathname: ctx.pathname, }, }; } catch (error) { ctx.res.statusCode = 404; ctx.res.end("Not found"); return; } } ); export default wrapper.withRedux(MyApp);
执行yarn build命令后,生成的_app chunk体积约为431kb,体积过大。请问我是否存在操作错误?该如何缩小这个chunk的体积?
解决方案
一、操作错误排查
你的代码本身没有语法或逻辑错误,但在资源引入和依赖处理上存在可优化空间,这是导致chunk体积过大的核心原因,而非操作失误。
二、具体优化方案
优化CSS引入
- 替换Ant Design全局样式引入:
import "antd/dist/antd.css"会打包完整的Ant Design样式,改用babel-plugin-import实现按需引入组件及对应样式,只打包实际用到的组件样式。 - 合并冗余CSS文件:检查
bootstrap.css、common.css等全局CSS是否有重复规则,合并后可减少体积冗余。 - 迁移局部样式方案:逐步改用CSS Modules(局部作用域)或Tailwind CSS(按需生成样式),避免全局CSS的无效代码。
- 替换Ant Design全局样式引入:
优化依赖打包
- 拆分Redux与API逻辑:检查
serverApi是否引入了不必要的Axios子模块,可拆分Redux的slice逻辑,避免在_app中集中引入过多非全局必需的代码。 - 替换轻量进度条:若
nextjs-progressbar非必需,可改用自定义轻量进度条实现,进一步减少依赖体积。
- 拆分Redux与API逻辑:检查
利用Next.js内置优化
- 开启精准树摇:确保
tsconfig.json中compilerOptions.module设置为ESNext,让Webpack更高效地剔除无用代码。 - 动态导入Layout组件:用
next/dynamic动态导入Layout并设置ssr: true,将Layout代码拆分到独立chunk,减轻_app的体积压力。 - 分析chunk构成:执行
yarn build --analyze生成体积分析报告,定位具体导致_app体积过大的依赖或代码块,针对性优化。
- 开启精准树摇:确保
优化第三方依赖
- 替换重依赖:若Bootstrap仅用到少量组件,可改用轻量替代方案,或只引入所需的Bootstrap模块。
- 升级依赖版本:将Ant Design、Redux等依赖升级到最新稳定版,新版本通常会包含体积优化。
三、补充建议
避免在_app.ts中引入非全局必需的资源,仅保留全局生效的代码与样式;将页面级样式迁移到对应页面组件中,减少全局CSS的冗余。
内容的提问来源于stack exchange,提问作者Najmus Sakib
相关产品推荐
相关产品推荐

