# 入口(Entry)
webpack 将创建所有应用程序的**依赖关系图表(dependency graph)**。图表的起点被称之为**入口起点(entry point)**。入口起点告诉 webpack 从哪里开始,并遵循着依赖关系图表知道要打包什么。可以将您应用程序的入口起点认为是根上下文(contextual root)或 app 第一个启动文件。
在 webpack 中,我们使用 webpack 配置对象(webpack configuration object) 中的` entry` 属性来定义入口。
一个最简单的例子:
webpack.config.js
~~~javascript
module.exports = {
entry: './path/to/my/entry/file.js'
};
~~~
这里有多种方式声明应用程序所需的特定 entry 属性。
## 单个入口(简写)语法
用法:`entry: string|Array<string>`
webpack.config.js
~~~javascript
const config = {
entry: './path/to/my/entry/file.js'
};
module.exports = config;
~~~
entry 属性的单个入口语法,是下面的简写:
~~~javascript
const config = {
entry: {
main: './path/to/my/entry/file.js'
}
};
~~~
> 向 entry 属性传入「文件路径(file path)数组」将创建“多个主入口(multi-main entry)”。在你想要多个依赖文件一起注入,并且将它们的依赖导向(graph)到一个“chunk”时,这种传入数组的方式比较有效。
当你正在寻找为「一个应用程序或只有一个入口起点的工具(即 library)」快速设置一个 webpack 配置的时候,这会是个很不错的选择。但是,使用此语法扩展(extend or scale)配置没有太多的灵活性。
## 对象语法
用法:entry: {[entryChunkName: string]: string|Array<string>}
webpack.config.js
~~~javascript
const config = {
entry: {
app: './src/app.js',
vendors: './src/vendors.js'
}
};
~~~
对象语法会比较繁琐。然而,这是应用程序中定义入口的最可扩展的方式。
> “可扩展的 webpack 配置”是指,可重用并且可以与其他配置组合使用。这是一种流行的技术,用于将关注点(concern)从环境(environment)、构建目标(build target)、运行时(runtime)中分离。然后使用专门的工具(如 webpack-merge)将它们合并。
## 常见场景
以下列出入口配置和它们的实际用例:
### 分离 应用程序(app) 和 公共库(vendor) 入口
webpack.config.js
~~~javascript
const config = {
entry: {
app: './src/app.js',
vendors: './src/vendors.js'
}
};
~~~
**1. 原理**
从表面上看,这告诉我们 webpack 从 app.js 和 vendors.js 开始创建依赖图表(dependency graph)。这些图表是彼此完全分离、互相独立的(每个 bundle 中都有一个 webpack 引导(bootstrap))。这种方式比较常见于只有一个入口起点(不包括 vendor)的单页应用程序(single page application)中。
**2. 原因**
这样设置允许你使用 `CommonsChunkPlugin` 从「应用程序 bundle」中提取 vendor 引用(vendor reference) 到 vendor bundle,并把 vendor 引用的部分替换为` __webpack_require__() `调用。如果应用程序 bundle 中没有 vendor 代码,那么你可以在 webpack 中实现被称为**长效缓存**的通用模式。
### 多个页面应用程序
webpack.config.js
~~~javascript
const config = {
entry: {
pageOne: './src/pageOne/index.js',
pageTwo: './src/pageTwo/index.js',
pageThree: './src/pageThree/index.js'
}
};
~~~
我们告诉 webpack 需要 3 个独立分离的依赖图表(如上面的示例)。
在多页应用中,服务器将为你获取一个新的 HTML 文档。页面重新加载新文档,并且资源被重新下载。然而,这给了我们特殊的机会去做很多事:
* 使用 `CommonsChunkPlugin` 为每个页面间的应用程序共享代码创建 bundle。由于入口起点增多,多页应用能够在入口起点重用大量代码/模块,这样可以极大的从这些这些技术受益。
# 输出(Output)
此选项影响 compilation 对象的输出。output 选项控制 webpack 如何向硬盘写入编译文件。注意,即使可以存在多个入口起点,但只指定一个输出配置。
## 用法
在 webpack 中配置 output 属性的最低要求是,将它的值设置为一个对象,包括以下两点:
* 编译文件的文件名(filename),首选推荐:// main.js || bundle.js || index.js
* output.path 对应一个绝对路径,此路径是你希望一次性打包的目录。
webpack.config.js
~~~javascript
const config = {
output: {
filename: 'bundle.js',
path: '/home/proj/public/assets'
}
};
module.exports = config;
~~~
## 选项
output属性还有很多可选传入的值,具体可以访问[输出选项](https://doc.webpack-china.org/concepts/output/)
## 多个入口起点
如果配置创建了多个单独的 "chunk"(例如,使用多个入口起点或使用像 CommonsChunkPlugin 这样的插件),则应该 **使用占位符(substitutions)** 来确保每个文件具有唯一的名称。
~~~
{
entry: {
app: './src/app.js',
search: './src/search.js'
},
output: {
filename: '[name].js',
path: __dirname + '/dist'
}
}
// 写入到硬盘:./dist/app.js, ./dist/search.js
~~~
使用入口名称:
~~~
filename: "[name].bundle.js"
~~~
使用内部 chunk id
~~~
filename: "[id].bundle.js"
~~~
使用每次构建过程中,唯一的 hash 生成
~~~
filename: "[name].[hash].bundle.js"
~~~
使用基于每个 chunk 内容的 hash:
~~~
filename: "[chunkhash].bundle.js"
~~~
注意此选项被称为文件名,但是你还是可以使用像 "js/[name]/bundle.js" 这样的文件夹结构。
注意,此选项不会影响那些「按需加载 chunk」的输出文件。对于这些文件,请使用 output.chunkFilename 选项来控制输出。同样也不影响通过 loader 创建的文件,对于这些文件,请查看 loader 选项来输出控制。
可以使用以下替换模板字符串(通过 webpack 内部的[TemplatedPathPlugin]TemplatedPathPlugin):
| 占位符 | 描述|
|---|---|
| [hash]| 模块标识符(module identifier)的 hash|
| [chunkhash]| chunk 内容的 hash|
| [name]| 模块名称|
| [id]| 模块标识符(module identifier)|
| [file]| 模块文件名称|
| [filebase]| 模块 basename|
| [query]| 模块的 query,例如,文件名 ? 后面的字符串|
`[hash] `和 `[chunkhash] `的长度可以使用 `[hash:16]`(默认为20)来指定。或者,通过指定`output.hashDigestLength` 在全局配置长度。