一、建立webpack项目目录如webpackDemo,并进入webpackDemo;css
二、 在node已经安装的前提下,打开命令行控制器,输入以下命令:html
npm init -y npm install webpack webpack-cli --save-dev //安装webpack webpack-cli (MacOS: sudo npm install webpack webpack-cli -g,sudo npm isntall webpack webpack-cli --save-dev)
命令执行结束后,会生成package.json、package_lock.json、node_modules文件。而后手动建立src目录与package.json平级,src目录下有index.html ,index.js 。node
注:npm使用的是淘宝镜像,使用命令 npm install --registry=https://registry.npm.taobao.org express (临时使用);webpack
(MacOS 若是上面命令不生效,能够使用此命令: npm config set registry https://registry.npm.taobao.org).es6
一、 webpack有四个核心概念:entry(入口) 、output(输出)、loader、plugin(插件)。web
告诉webpack构建内部依赖图开始的模块;能够指定单入口起点文件或多入口起点文件。正则表达式
module.exports = { entry:"./src/index.js"}
告诉webpack输出建立的bundles,以及如何命名文件。指定编译后的输出文件路径。express
const OUTPUT_FILE_NAME = "dist"module.exports = { entry:"./src/index.js", output: { filename: "[name].[contenthash:10].js", //输出文件名称, hash解决缓存问题 path: path.resolve(__dirname,'dist') //输出文件路径 } }
loader可让webpack能够处理非JavaScript文件,webpack自己只能处理JavaScript。npm
webpack配置loader有两个目标:json
a). test属性,用于被对应的loader进行转换的某个和某些文件;
b). use属性,表示进行转换时,应该使用哪一个loader;
module.exports = { output: { filename: "[name].[contenthash:10].js", //输出文件名称, hash解决缓存问题 path: path.resolve(__dirname, OUTPUT_FILE_NAME) //输出文件路径 }, module: { rules: [{ //整理html的img资源, test: /\.html$/, use: ["html-loader"] }, { //处理css资源 test: /\.css$/, use: ["css-loader", "style-loader"] }, { //处理JS资源 test: /\.jsx?$/, use: ['file-loader'] }] } }
loader用于转换某些类型,插件用于执行更普遍的任务。若使用一个插件,只需require(),而后添加到数组中。
module.exports = { ..., plugins: [ new HtmlWebpackPlugin({ template: "./src/index.html", hash: true }), new MiniCssExtarctPlugin({ filename: 'css/[name].[contenthash:10].css', path: path.resolve(__dirname,'dist') }) ] }
附所有代码:
package.json
{ "name": "webpack_demo", "version": "1.0.0", "description": "", "scripts": { "test": "echo \"Error: no test specified\" && exit 1", "watch": "webpack --watch", "start": "webpack --config webpack.config.js", "build": "webpack --config webpack.config.pro.js" }, "keywords": [], "author": "", "license": "ISC"}
webpack.config.js
const path = require("path"); const HtmlWebpackPlugin = require("html-webpack-plugin"); const MiniCssExtarctPlugin = require("mini-css-extract-plugin"); //将css从js中提取出来const OUTPUT_FILE_NAME = "dist"; module.exports = { entry: "./src/index.js", output: { filename: "[name].[contenthash:10].js", //输出文件名称,hash解决缓存问题,具体可见下面的解释 path: path.resolve(__dirname, OUTPUT_FILE_NAME) //输出文件路径 }, mode: "development", //开发环境,生产环境使用"production" module: { rules: [{ //整理html的img资源, test: /\.html$/, use: ["html-loader"] }, { //处理css资源 test: /\.css$/, use: [ //将css文件整合到JS文件中 "css-loader", //建立style标签,将样式放入 "style-loader", // css兼容性处理:postcss-->postcss-loader postcss-preset-env ] }, { //处理JS资源 test: /\.js$/, exclude: /node_modules/, //处理除了nodde_modules里的js文件 loader: 'babel-loader' //用babel-loader处理 }, { //处理图片资源 test: /\.(png|svg|jpg|gif)$/, use: ['file-loader'] }, { // exclude: /\.(css|js|html)$/, //排除正则内的资源 test: /\.(png|svg|jpg|gif)$/, // 这里是匹配条件,每一个选项都接收一个正则表达式或字符串 // test 和 include 具备相同的做用,都是必须匹配选项 // exclude 是必不匹配选项(优先于 test 和 include) // 最佳实践: // - 只在 test 和 文件名匹配 中使用正则表达式 // - 在 include 和 exclude 中使用绝对路径数组 // - 尽可能避免 exclude,更倾向于使用 include use: ['file-loader'], // options: { // name: "[hash:10].[ext]" //名字太长进行截取 // } } ] }, resolve: { extensions: ['.js', '.json'] }, /* source-map:外联 inline-source-map : */ devtool: "source-map", //告诉webpack提供源代码 plugins: [ // 将CSS文件从JS文件中提取出来 new MiniCssExtarctPlugin({ filename: 'css/[name].[contenthash:10].css', path: path.resolve(__dirname, OUTPUT_FILE_NAME) }), new HtmlWebpackPlugin({ template: "./src/index.html" }) ], devServer: { port: 5000, //端口号 contentBase: OUTPUT_FILE_NAME, //可访问问文件 hot: true, //开启HMR热更新 https: true, //使用https compress: true, // 启用压缩 // proxy: { // "/": "http://localhost:3000", //使用代理路径 // } }, /** code splitting 代码分割 * 当单入口时,能够将 node_modules中代码单独打包成一个chunk; * 当多入口时,提取公共文件单独打包成一个chunk; */ optimization: { splitChunks: { chunks: "all" } } /** * 缓存: * Babel缓存 * cacheDirectory:true * -->让第二次打包更快 * 文件资源缓存: * hash :每次webpack构建是会生成一个惟一的hash值; * 问题:js和css使用同一个hash值,会致使缓存失效,可能值改变一个文件; * chunkhash:根据chunk生成的hash值,若是打包来自同一个chunk,那么hash是同样的 * 问题:chunkhash是同样的,由于css是在js中被引用的,属于同一个chunk; * contenthash:根据文件内容生成hash值,不一样文件的hash值不同; * -->让代码上线运行缓存更好使用 * */ /** * tree shaking:去除无用代码 * 前提: 1.必须使用ES6模块化 2.开启production环境 * 做用: 减小代码体积 * * 在package.json中设置: * sideEffects:false 全部代码都没有反作用(均可以进行tree shaking) * 问题:可能会把css @babel/polyfill(反作用)文件干掉 * sideEffects:["*.css",".less"] 不会进行tree shaking */ /** * HMR :hot module replacement 热模块 * 做用:一个模块发生变化指挥从新打包这个模块,并不从新打包全部。提升打包速度。 * 样式文件:能够经过HMR实现,style-loader已实现 * JS文件:默认不使用HMR功能-->修改JS文件代码,只能处理非入口文件。 * if(module.hot){ * module.hot.accept("index.js",()=>{ * //监听文件变化,一旦发生变法,其余地方不会从新打包,直接执行回调 * })) * } * Html文件:默认不使用HMR功能,同时会出问题(无需作HMR功能) * 解决方案:修改entry入口,引入html文件 * * */}
wenpack.config.pro.js
const path = require("path"); const HtmlWebpackPlugin = require("html-webpack-plugin"); const MiniCssExtarctPlugin = require("mini-css-extract-plugin"); //将css从js中提取出来const OptiminizeCssAssetsPlugin = require("optimize-css-assets-webpack-plugin"); //压缩CSSconst UglifyJsPlugin = require("uglifyjs-webpack-plugin"); const OUTPUT_FILE_NAME = "dist"; module.exports = { entry: "./src/index.js", output: { filename: "js/[name].[contenthash:10].js", //输出文件名称,hash解决缓存问题,具体可见下面的解释 chunkFilename: 'js/[name].[contenthash:10].bundle.js', // 依赖文件名称 path: path.resolve(__dirname, OUTPUT_FILE_NAME), //输出文件路径 publicPath: '/' // 公共路径 }, mode: "production", //生产环境 module: { rules: [{ test: /\.html$/, use: ["html-loader"] }, { test: /\.css$/, use: [MiniCssExtarctPlugin.loader, "css-loader"] }, { test: /\.jsx?$/, exclude: /node_modules/, //处理除了nodde_modules里的js文件 loader: 'babel-loader' //用babel-loader处理es6 }, { test: /\.(png|svg|jpg|gif)$/, use: ['file-loader'], } ] }, devtool: "source-map", //告诉webpack提供源代码 plugins: [ new HtmlWebpackPlugin({ template: "./src/index.html", hash: true }), new MiniCssExtarctPlugin({ filename: 'css/[name].[contenthash:10].css', path: path.resolve(__dirname, OUTPUT_FILE_NAME) }), /** * optimize-css-assets-webpack-plugin 会使webpack中自带的JS压缩失效,须要从新配置UglifyJsPlugin */ new OptiminizeCssAssetsPlugin(), ], /** code splitting 代码分割 * 当单入口时,能够将 node_modules中代码单独打包成一个chunk; * 当多入口时,提取公共文件单独打包成一个chunk; */ optimization: { splitChunks: { chunks: "all" } } }