若愚老师
安装
//全局安装
npm install -g webpack
//安装到你的项目目录
npm install --save-dev webpack
要安装最新版本或特定版本,请运行以下命令之一:
npm install --save-dev webpack
npm install --save-dev webpack@<version>
首先我们创建一个目录,初始化 npm,然后 在本地安装 webpack,接着安装 webpack-cli(此工具用于在命令行中运行 webpack):
mkdir webpack-demo && cd webpack-demo
npm init -y
npm install webpack webpack-cli --save-dev
- 通过命令行模式实现
webpack可以在终端中使用,在基本的使用方法如下:
// {extry file}出填写入口文件的路径,本文中就是上述main.js的路径,
// {destination for bundled file}处填写打包文件的存放路径
// 填写路径的时候不用添加{}
webpack {entry file} {destination for bundled file}
指定入口文件后,webpack
将自动识别项目所依赖的其它文件,不过需要注意的是如果你的webpack
不是全局安装的,那么当你在终端中使用此命令时,需要额外指定其在node_modules
中的地址,继续上面的例子,在终端中输入如下命令
// webpack非全局安装的情况
node_modules/.bin/webpack app/main.js public/bundle.js
- 通过配置文件来使用
Webpack
根目录下新建一个名为webpack.config.js
的文件
module.exports = {
entry: __dirname +"app.js",//已多次提及的唯一入口文件
output: {
path: __dirname + "/public",//打包后的文件存放的地方
filename: "bundle.js"//打包后输出文件的文件名
}
}
注:
“__dirname”
是node.js
中的一个全局变量,它指向当前执行脚本所在的目录
有了这个配置之后,再打包文件,只需在终端里运行webpack
(非全局安装需使用node_modules/.bin/webpack
)命令就可以了,这条命令会自动引用webpack.config.js
文件中的配置选项
有了这个配置之后,再打包文件,只需在终端里运行webpack(非全局安装需使用node_modules/.bin/webpack
)命令就可以了,这条命令会自动引用webpack.config.js
文件中的配置选项
更快捷的执行打包任务
在命令行中输入命令需要代码类似于node_modules/.bin/webpack
这样的路径比较麻烦,通过npm进行配置后可以在命令行中使用简单的npm start
命令来替代上面略微繁琐的命令。在package.json
中对scripts
对象进行相关设置即可:
{
"name": "webpack-sample-project",
"version": "1.0.0",
"description": "Sample webpack project",
"scripts": {
"start": "webpack" // 修改的是这里,JSON文件不支持注释,引用时请清除
},
"author": "zhang",
"license": "ISC",
"devDependencies": {
"webpack": "3.10.0"
}
}
loaders
loaders官方文档
通过使用不同的loader
,webpack
有能力调用外部的脚本或工具,实现对不同格式的文件的处理,比如说分析转换scss
为css
,或者把下一代的JS文件(ES6,ES7)转换为现代浏览器兼容的JS文件
Loaders
需要单独安装并且需要在webpack.config.js
中的modules
关键字下进行配置,Loaders
的配置包括以下几方面:
-
test
:一个用以匹配loaders所处理文件的拓展名的正则表达式(必须) -
loader
:loader的名称(必须) -
include/exclude
:手动添加必须处理的文件(文件夹)或屏蔽不需要处理的文件(文件夹)(可选); -
query
:为loaders
提供额外的设置选项(可选)
举个栗子:babel-loader
安装:
// webpack 3.x | babel-loader 8.x | babel 7.x
npm install babel-loader@8.0.0-beta.0 @babel/core @babel/preset-env webpack
// webpack 3.x babel-loader 7.x | babel 6.x
npm install babel-loader babel-core babel-preset-env webpack
module.exports = {
entry: __dirname +"app.js",//已多次提及的唯一入口文件
output: {
path: __dirname + "/public",//打包后的文件存放的地方
filename: "bundle.js"//打包后输出文件的文件名
},
module: {
rules: [
{
test: /\.js$/,
exclude: /(node_modules|bower_components)/,
use: {
loader: 'babel-loader',
options: {
presets: ['@babel/preset-env']
}
}
}
]
}
}
插件(Plugins)
- 插件(Plugins)是用来拓展Webpack功能的,它们会在整个构建过程中生效,执行相关的任务。
Loaders和Plugins常常被弄混,但是他们其实是完全不同的东西,可以这么来说,loaders是在打包构建过程中用来处理源文件的(JSX,Scss,Less..),一次处理一个,插件并不直接操作单个文件,它直接对整个构建过程其作用。 - 要使用某个插件,我们需要通过npm安装它,然后要做的就是在webpack配置中的plugins关键字部分添加该插件的一个实例(plugins是一个数组)
- 几个常用的插件:
-
HtmlWebpackPlugin
:这个插件的作用是依据一个简单的index.html模板,生成一个自动引用你打包后的JS文件的新index.html。这在每次生成的js文件名称不同时非常有用(比如添加了hash值)。
npm install --save-dev html-webpack-plugin
-
Hot Module Replacement
:(HMR)也是webpack里很有用的一个插件,它允许你在修改组件代码后,自动刷新实时预览修改后的效果。
-
webpack从入门到精通
git clone git@github.com:slashhuang/webpack2-tutorial.git
cd webpack2-tutorial
cnpm i --verbose //安装所有依赖
cnpm i -g anywhere
anywhere //随时随地将你的当前目录变成一个静态文件服务器的根目录
command.js
文件中的配置configFile.watch = true;
entry
:
webpack.config.js:
module.exports = {
entry:{
index:'./index.js',
index1:'./index1.js'
},
output: {
path: path.resolve(__dirname, 'dist'),
filename: '_[name].js'
}
};
output:
webpack.config.js:
let base = {
index:'./index.js?t=2',
index1:'./index1.js'
};
//webpack2 提供了多种配置方案
module.exports = {
entry:base,
output: {
//导出目录
path: path.resolve(__dirname, 'uuudist'), // 必须是绝对路径
publicPath: "/output/uuudist/", // server-relative
//包规范格式
libraryTarget:'umd',
library: "MyLibrary",
//文件名
chunkFilename:'[chunkhash]_[name].js', //用来异步加载
//hash位数
hashDigestLength:3,
//导出文件
//hash ==> webpack编译过程
// chunkhash => webpack对每个文件的hash
filename: '_[name][chunkhash].js' //'_[name][chunkhash:3].js'
//name是entry里面的key
}
};
[chunkhash]
类似时间戳,区分缓存文件 每一次文件内容的改变都会使hash值改变,因此以这种方式命名文件无法去重,文件是增量的
devtool:
devtool: 'source-map',//资源映射表 chrome debug==>
or
devtool: 'cheap-source-map'
loaders:
module:{
//entry => loaders ==> webpack ==> output
rules:[
{
test: /\.js[x]?$/,
exclude: /node_modules/,
use: {
loader:'babel-loader'
}
},
{
test: /\.css$/,
use: ExtractTextPlugin.extract({
fallback: "style-loader",
use:{
loader:'css-loader',
options: {
sourceMap: true
}
}
})
},
{
test: /\.less$/,
use: ExtractTextPlugin.extract({
fallback:'style-loader',
use:['css-loader',{
loader:'less-loader',
options: {
sourceMap: true
}
}]
})
},
{
test: /\.scss$/,
use: ExtractTextPlugin.extract({
fallback:'style-loader',
use:['css-loader',{
loader:'sass-loader',
options: {
sourceMap: true
}
}]
})
},
{
test: /\.(png|jpg|jpeg|gif|woff|woff2|ttf|eot|svg|swf)$/,
use: {
loader:'file-loader',
options:{
name:'[name]_[sha512:hash:base64:7].[ext]'
}
}
},
{
test: /\.html/,
use:{
loader:"html-loader",
options:{
minimize: false,
attrs:false
}
}
}
]
}
output:
plugins:[
new webpack.ProvidePlugin({
$: 'jquery'
}),
new WebpackNotifierPlugin({ //编译成功会有提示
title: 'Webpack 编译成功',
contentImage: path.resolve(process.cwd(), './img/avatar.jpeg'),
alwaysNotify: true
}),
new ExtractTextPlugin({
filename: "[name].css",
disable: false,
allChunks: true
}),
new webpack.optimize.CommonsChunkPlugin({
name: 'common',
minChunks: Infinity
})
],