Sources中main、vendors、runtime、polyfills、scripts这些是什么?
非常棒的问题 👏👏
你现在已经在真正理解 现代前端构建体系 的内部逻辑了。
这些文件名(main.js, vendors.js, runtime.js, polyfills.js, scripts.js)
其实不是随意起的,而是构建工具(如 Webpack、Vite、Angular CLI、Next.js 等)
在打包过程中**自动分块(chunk split)**的结果。
下面我给你详细解释每一个的含义与作用👇
🧩 一、这些文件的本质:打包后的「代码分块」 (bundle chunks)
现代网站不是加载一个巨大的 app.js,而是被拆分成多个部分:
| 文件名 | 作用 | 谁生成的 |
|---|---|---|
| main.js | 你的应用主逻辑(你写的业务代码) | 由打包器生成 |
| vendors.js | 第三方库代码(React、Vue、lodash、axios 等) | 由打包器自动抽取 |
| runtime.js | Webpack 或 Vite 的运行时引导逻辑 | 由打包器自动生成 |
| polyfills.js | 为兼容老浏览器而注入的垫片代码 | 框架或工具自动生成 |
| scripts.js | 额外脚本(例如配置、全局注册、第三方 SDK) | 可由开发者或工具添加 |
🧠 二、逐个深入理解
🟦 1. main.js
👉 你的核心业务逻辑。
包含:
- 你自己写的应用代码;
- 页面、组件、路由逻辑;
- 样式导入、初始化脚本等。
例如 React 项目:
import ReactDOM from 'react-dom';
import App from './App';
ReactDOM.render(<App />, document.getElementById('root'));
这些内容最终都会进 main.js。
🟩 2. vendors.js
👉 外部依赖(第三方库)。
比如:
react,react-domvueaxioslodashmomentecharts- 甚至第三方 SDK
原因:
这些库变化频率低,但体积大。
把它们单独抽离出来后,浏览器就能缓存
vendors.js,而不必每次都重新下载。
Webpack 配置里一般是这样做的:
optimization: {splitChunks: {cacheGroups: {vendors: {test: /[\\/]node_modules[\\/]/,name: 'vendors',chunks: 'all',},},},
}
🟨 3. runtime.js
👉 Webpack(或其他打包器)的运行时引导代码。
内容包括:
- 模块加载函数(例如
_webpack_require_()) - chunk 依赖管理;
- 异步加载逻辑(动态 import);
- 哈希文件版本匹配。
可以理解为:
Webpack 自己的小型「操作系统」,
负责加载、执行、缓存 JS 模块。
一般只有几 KB。
🟧 4. polyfills.js
👉 浏览器兼容性补丁(垫片)。
不同浏览器支持的 JS 特性不同,比如:
- 老版 IE 不支持
Promise、fetch、Object.assign; - Safari 不支持某些 ES6 语法。
polyfills.js 里通常包含:
import 'core-js/stable';
import 'regenerator-runtime/runtime';
让新语法在旧浏览器上也能正常运行。
🟥 5. scripts.js
👉 额外注入的全局脚本。
不是框架代码,而是一些额外的独立 JS,比如:
- Google Analytics / 百度统计;
- 配置文件;
- 初始化脚本;
- 广告脚本。
在 Angular 或某些脚手架项目中,这些通过配置文件指定:
"scripts": ["src/assets/js/analytics.js","src/assets/js/custom.js"
]
这些脚本最终被合并为 scripts.js。
⚙️ 三、为什么要这样拆分?
| 原因 | 作用 |
|---|---|
| ✅ 缓存优化 | 第三方库变化少,主逻辑变化多,拆分后缓存效率更高 |
| ⚡ 加载性能 | 首屏只加载必要部分,其他延迟加载 |
| 🧩 模块化管理 | 方便代码维护、按需加载 |
| 🔄 热更新支持 | 改一处代码不用重新加载所有资源 |
📊 举个真实的例子(以 Angular 项目为例)
构建后生成的文件结构:
dist/
├── runtime.7fabc1.js // Webpack运行时
├── polyfills.5e2d3a.js // 浏览器兼容补丁
├── main.3b91e4.js // 应用主逻辑
├── vendors.2d91cc.js // 第三方库
├── scripts.f984b2.js // 额外全局脚本
├── styles.7f83c1.css // 样式
加载顺序(在 HTML 中):
<script src="runtime.7fabc1.js" defer></script>
<script src="polyfills.5e2d3a.js" defer></script>
<script src="vendors.2d91cc.js" defer></script>
<script src="main.3b91e4.js" defer></script>
<script src="scripts.f984b2.js" defer></script>
✅ 总结一句话
| 文件 | 内容 | 作用 |
|---|---|---|
main.js | 应用主逻辑 | 你写的业务代码 |
vendors.js | 第三方库 | 缓存优化、抽离依赖 |
runtime.js | 模块加载引导 | 打包器的运行机制 |
polyfills.js | 浏览器兼容性代码 | 兼容旧浏览器 |
scripts.js | 外部或全局脚本 | 分析、广告、配置等 |
如果你愿意,我可以帮你画一个图(流程图或加载结构图),
直观地展示这些文件之间的关系——从加载到执行的顺序。
要我帮你画出来吗?
