动态引入依赖需显式配置optimizedeps.include声明(如'monaco-editor/esm/vs/editor/editor.api'),exclude已兼容esm的轻量包(如vue、dayjs),配合entries指定动态入口路径并稳定缓存,实现精准预构建。

动态引入(如 import())的依赖,Vite 默认扫描不到,导致首次加载时才临时构建,卡顿明显。解决核心是让这些依赖在启动前就进入预构建流程——关键靠 optimizeDeps.include 显式声明,同时配合 exclude 避免干扰。
include:只加真正需要预构建的动态依赖
不是所有动态导入都要加,只加那些体积大、格式旧(CJS)、或路径深的包。Vite 不会自动识别 import('./utils/worker.js') 或 import('monaco-editor/esm/vs/editor/editor.api') 这类写法,必须手动列进 include。
-
按需子路径优先:比如用到 Monaco 的编辑器 API,写
'monaco-editor/esm/vs/editor/editor.api',而不是'monaco-editor'—— 后者会触发整包构建,耗时翻倍 -
避免模糊匹配:不写
'lodash-*'或'@mylib/*',除非你确认项目中所有匹配项都需预构建;否则易引入冗余 -
链接依赖也要加:monorepo 中通过
pnpm link或yarn link引入的本地包,若非 ESM 格式,必须加进include,否则运行时报错
exclude:跳过已兼容、轻量或纯 ESM 的依赖
排除的目的是减少预构建工作量,但前提是它真能被浏览器直接加载。误排 CJS 包会导致 not a module 错误。
-
确认 ESM 格式再排除:查包的
package.json,有"type": "module"或带"exports"字段(且指向 ESM 入口)才算安全,如vue、vue-router@4+、dayjs -
别 exclude CJS 依赖的上游:比如某个 ESM 包(
esm-dep)内部依赖了cjs-dep,这时不能 excludeesm-dep,而应把cjs-dep加进include -
大型包可考虑 CDN 替代:像
jspdf、pdfjs-dist这类体积巨大又极少改动的库,exclude 后用 script 标签引入更高效
配合 entries 和缓存提升稳定性
仅靠 include/exclude 不够,还需确保 Vite 能扫到所有动态入口,并让预构建结果持久可用。
-
显式声明动态入口:如果动态 import 分散在多个文件(如插件、工具函数),用
optimizeDeps.entries指定路径模式,例如['src/plugins/**/*.{js,ts}'],避免漏检 -
缓存目录移到项目内:CI 或频繁重装 node_modules 时,默认
node_modules/.vite易丢失。配置cacheDir: './node_modules/.vite-cache'并加进.gitignore,让缓存稳定复用 -
调试时再 force,日常不用:
optimizeDeps.force: true会让每次启动清缓存重来,反而拖慢;只在 CI 构建或验证预构建行为时临时启用
配置本质是“精准干预”——让 Vite 在启动前就知道哪些依赖必须处理、哪些可以绕过,而不是靠猜。动线清晰了,首次加载卡顿自然消失。











