const path = require('path');
const webpack = require('webpack');
// 刪除已經更改標籤
const CleanWebpackPlugin = require('clean-webpack-plugin');
// 分離CSS
// const ExtractTextPlugin = require("extract-text-webpack-plugin");// webpack3
const MiniCssExtractPlugin = require("mini-css-extract-plugin"); // webpack4
// 在 HTML 中新增標籤
const HtmlWebpackPlugin = require("html-webpack-plugin");
// 使用optimize-css-assets-webpack-plugin壓縮單獨的css檔案
const optimizeCss = require('optimize-css-assets-webpack-plugin');
//使用uglify-js進行js檔案的壓縮
const UglifyJsPlugin = require("uglifyjs-webpack-plugin");
// 自動補全CSS字首
const autoprefixer = require('autoprefixer');
// vue 外掛
const VueLoaderPlugin = require('vue-loader/lib/plugin')
// 這是 packet.json 中 dependencies 下的
const VENOR = [
"lodash",
]
module.exports = {
// bundle 和 vendor 都是自己隨便取名的,會對映到 [name] 中
entry: {
bundle: "./src/index.js",
vendor: VENOR
}, // 入口檔案
output: {
path: path.resolve(__dirname, '../dist'), // 必須使用絕對地址,輸出資料夾
// 既然我們希望快取生效,就應該每次在更改程式碼以後修改檔名
// [chunkhash]會自動根據檔案是否更改而更換雜湊
filename: '[name].[hash].js', // 打包後輸出檔案的檔名
publicPath: process.env.NODE_ENV === 'production' ? "./" : "/" // 知道如何尋找資源
},
module: {
rules: [{
// js檔案使用babel
test: /\.js$/,
use: "babel-loader",
exclude: /node_modules/,
},
{
test: /\.html$/,
loader: 'html-loader'
},
{
test: /\.vue$/,
loader: 'vue-loader'
},
{
test: /\.(png|jpg|jpeg|gif)$/,
use: [{
loader: "url-loader",
options: {
name: "[name]-[hash:5].min.[ext]",
limit: 1000, // size <= 1KB
publicPath: "static/",
outputPath: "static/"
}
}, ]
},
// 處理字型檔案
{
test: /\.(otf|eot|svg|ttf|woff|woff2)$/,
use: [{
loader: 'url-loader',
options: {
name: '[name].[ext]', // 打包後的檔名稱
outputPath: '', // 預設是dist目錄
publicPath: 'dist/fonts', // 圖片的url前面追加'dist/images'
useRelativePath: true, // 使用相對路徑
limit: 50000 // 表示小於1K的圖片會被轉化成base64格式
}
}]
},
// webpack 3
// {
// test: /\.css$/,
// loader: ExtractTextPlugin.extract({
// // 必須這樣寫,否則會報錯
// fallback: 'style-loader',
// use: [{
// loader: 'css-loader',
// options: {
// modules: true
// }
// }]
// })
// },
// webpack4
{
test: /\.css$/,
use: [
MiniCssExtractPlugin.loader, // replace ExtractTextPlugin.extract({..})
"css-loader",
"postcss-loader"
]
},
// {
// test: /\.less$/,
// loader: ExtractTextPlugin.extract({
// // 必須這樣寫,否則會報錯
// fallback: 'style-loader',
// use: [
// "css-loader",
// "less-loader"
// ]
// })
// }, // webpack3
{
test: /\.less$/,
exclude: '/node_modules',
use: [{
loader: 'style-loader'
},
{
loader: MiniCssExtractPlugin.loader
},
{
loader: 'css-loader',
options: {
importLoaders: 1
}
},
{
loader: 'postcss-loader',
options: {
ident: 'postcss',
plugins: (loader) => [
require('postcss-import')({ root: loader.resourcePath }),
require('postcss-cssnext')(),
require('cssnano')()
]
}
},
{
loader: 'less-loader', //
options: {
importLoaders: 1
}
}
]
},
]
},
resolve: { //解析模組的可選項
modules: [
"node_modules",
path.resolve(__dirname, 'src')
],
extensions: [".wasm", ".mjs", ".js", ".json", ".jsx"],
alias: { //模組別名列表
utils: path.resolve(__dirname, 'src/uils')
}
},
// webpack4 用來代替webpack.optimize.CommonsChunkPlugin
optimization: {
runtimeChunk: {
name: 'manifest'
},
minimizer: [
// UglifyJsPlugin
// cache 啟用檔案快取。預設的快取路徑為: node_modules/.cache/uglifyjs-webpack-plugin.
// cacheKeys 允許重寫預設的cache keys.
// parallel 使用多程式並行執行來提高構建速度。預設併發執行次數:os.cpus().length- 1。
// sourceMap 使用sourceMap將錯誤訊息位置對映到模組(這會減慢編譯速度)。如果您使用自己的minify函式,請閱讀minify部分以正確處理sourceMap。
// minify 允許覆蓋預設的minify函式。預設外掛使用uglify-js包。
// uglifyOptions
// extractComments 啟用/禁用提取註釋
new UglifyJsPlugin({
cache: true,
parallel: true,
sourceMap: true,
exclude: /node_modules/,
uglifyOptions: {
warnings: false,
parse: {},
compress: {},
mangle: true, // Note `mangle.properties` is `false` by default.
output: null,
toplevel: false,
nameCache: null,
ie8: false,
keep_fnames: false,
},
extractComments: true,
}),
//壓縮CSS
new optimizeCss({
cssProcessor: require('cssnano'), //引入cssnano配置壓縮選項
cssProcessorOptions: {
discardComments: { removeAll: true }
},
canPrint: true //是否將外掛資訊列印到控制檯
}) // 普通壓縮
],
splitChunks: {
chunks: "initial", // 必須三選一: "initial" | "all"(預設就是all) | "async"
minSize: 0, // 最小尺寸,預設0
minChunks: 1, // 最小 chunk ,預設1
maxAsyncRequests: 1, // 最大非同步請求數, 預設1
maxInitialRequests: 1, // 最大初始化請求書,預設1
name: () => {}, // 名稱,此選項課接收 function
cacheGroups: { // 這裡開始設定快取的 chunks
priority: "0", // 快取組優先順序 false | object |
vendor: { // key 為entry中定義的 入口名稱
chunks: "initial", // 必須三選一: "initial" | "all" | "async"(預設就是非同步)
test: /react|lodash/, // 正則規則驗證,如果符合就提取 chunk
name: "vendor", // 要快取的 分隔出來的 chunk 名稱
minSize: 0,
minChunks: 1,
enforce: true,
maxAsyncRequests: 1, // 最大非同步請求數, 預設1
maxInitialRequests: 1, // 最大初始化請求書,預設1
reuseExistingChunk: true // 可設定是否重用該chunk(檢視原始碼沒有發現預設值)
},
css: {
name: 'css',
test: /\.css$/,
chunks: 'all',
enforce: true
},
less: {
name: 'less',
test: /\.less$/,
chunks: 'all',
enforce: true
}
}
}
},
// 外掛列表
plugins: [
new VueLoaderPlugin(),
// 輸出的檔案路徑
// new ExtractTextPlugin("css/[name].[hash].css"), // webpack 3
new MiniCssExtractPlugin({
// Options similar to the same options in webpackOptions.output
// both options are optional
filename: "[name].css",
chunkFilename: "style/[name].[id].[hash].css"
}), // webpack 4
// new webpack.optimize.CommonsChunkPlugin({
// // vendor 的意義和之前相同
// // manifest檔案是將每次打包都會更改的東西單獨提取出來,保證沒有更改的程式碼無需重新打包,這樣可以加快打包速度
// names: ['vendor', 'manifest'],
// // 配合 manifest 檔案使用
// minChunks: Infinity
// }), // webpack4棄用
// 只刪除 dist 資料夾下的 bundle 和 manifest 檔案
new CleanWebpackPlugin(['dist/bundle.*.js', 'dist/less.*.js', 'dist/css.*.js', 'dist/vendor.*.js', 'dist/styles.*.js', 'dist/style/css.*.css', 'dist/style/less.*.css', "dist/manifest.*.js"], {
// 列印 log
verbose: true,
// 刪除檔案
dry: false
}),
// 注意在之前 HTML 檔案中請務必刪除之前引入的 JS 檔案
/**title : 用於生成的HTML檔案的標題。
filename : 用於生成的HTML檔案的名稱,預設是index.html。你可以在這裡指定子目錄(例如:assets/admin.html)
template : 模板的路徑。支援載入器,例如 html!./index.html。
inject :true | ‘head’ | ‘body’ | false 。把所有產出檔案注入到給定的 template或templateContent。當傳入 true或者 ‘body’時所有javascript資源將被放置在body元素的底部,“head”則會放在head元素內。
favicon : 給定的圖示路徑,可將其新增到輸出html中。
minify : {…} | false 。傳一個html-minifier 配置object來壓縮輸出。
hash : true | false。如果是true,會給所有包含的script和css新增一個唯一的webpack編譯hash值。這對於快取清除非常有用。
cache : true | false 。如果傳入true(預設),只有在檔案變化時才 傳送(emit)檔案。
showErrors : true | false 。如果傳入true(預設),錯誤資訊將寫入html頁面。
chunks : 只允許你新增chunks 。(例如:只有單元測試塊 )
chunksSortMode : 在chunk被插入到html之前,你可以控制它們的排序。允許的值 ‘none’ | ‘auto’ | ‘dependency’ | {function} 預設為‘auto’.
excludeChunks : 允許你跳過一些chunks(例如,不要單元測試的 chunk).
xhtml : 用於生成的HTML檔案的標題。
title : true | false。如果是true,把link標籤渲染為自閉合標籤,XHTML要這麼幹的。預設false。
*/
new HtmlWebpackPlugin({
filename: path.resolve(__dirname, "../dist/index.html"),
template: './index.html',
inject: 'body',
minify: {
removeComments: true, //移除註釋
collapseWhitespace: true, // 壓縮空白節點
collapseInlineTagWhitespace: true, //壓縮行級元素的空白,會保留 和實體空格
}
}),
new webpack.ProvidePlugin({
_: 'lodash',
}),
new webpack.HotModuleReplacementPlugin()
],
devServer: {
host: 'localhost', //伺服器的ip地址
port: 8080, //埠
open: true, //自動開啟頁面
hot: true, //開啟熱更新
inline: true
}
}
複製程式碼
對應的package.json
{
"name": "a-vue",
"version": "1.0.0",
"description": "",
"private": true,
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1",
"build": "webpack --profile --progress --colors --mode production --config config/webpack.base.js",
"dev": "webpack-dev-server --mode development --config config/webpack.base.js"
},
"author": "wy",
"license": "ISC",
"dependencies": {
"babel-plugin-transform-runtime": "^6.23.0",
"babel-preset-es2015": "^6.24.1",
"babel-preset-stage-2": "^6.24.1",
"happypack": "^5.0.0",
"lodash": "^4.17.2",
"vue": "^2.5.21"
},
"devDependencies": {
"autoprefixer": "^9.4.3",
"babel-core": "^6.26.0",
"babel-loader": "^7.1.2",
"babel-preset-env": "^1.6.0",
"babel-preset-react": "^6.16.0",
"clean-webpack-plugin": "^1.0.0",
"css-loader": "^0.28.11",
"cssnano": "^4.1.8",
"extract-text-webpack-plugin": "^4.0.0-beta.0",
"file-loader": "^1.1.11",
"html-loader": "^0.5.5",
"html-webpack-plugin": "^4.0.0-beta.3",
"imagemin": "^5.3.1",
"imagemin-pngquant": "^5.1.0",
"img-loader": "^2.0.0",
"less": "^3.9.0",
"less-loader": "^4.1.0",
"mini-css-extract-plugin": "^0.5.0",
"optimize-css-assets-webpack-plugin": "^5.0.1",
"postcss-cssnext": "^3.1.0",
"postcss-import": "^12.0.1",
"postcss-loader": "^2.1.6",
"postcss-sprites": "^4.2.1",
"style-loader": "^0.18.2",
"uglifyjs-webpack-plugin": "^2.1.0",
"url-loader": "^1.0.1",
"vue-loader": "^15.4.2",
"vue-style-loader": "^4.1.2",
"vue-template-compiler": "^2.5.21",
"webpack": "^4.16.0",
"webpack-cli": "^3.0.8",
"webpack-dev-server": "^3.1.14"
}
}
複製程式碼