vue-cli 專案 webpack.prod.conf.js 檔案程式碼註釋
阿新 • • 發佈:2019-02-07
// 生產模式配置檔案 webpack.prod.conf.js // 註釋參考 https://www.cnblogs.com/ye-hcj/p/7082620.html 和 https://yq.aliyun.com/articles/609824 和 https://segmentfault.com/a/1190000012472099 'use strict' // 下面是引入nodejs的路徑模組 const path = require('path') // 下面是utils工具配置檔案,主要用來處理css類檔案的loader const utils = require('./utils') // 下面引入webpack,來使用webpack內建外掛 const webpack = require('webpack') // 下面是config目錄下的index.js配置檔案,主要用來定義了生產和開發環境的相關基礎配置 const config = require('../config') // 下面是webpack的merger外掛,主要用來處理配置物件合併的,可以將一個大的配置物件拆分成幾個小的,合併,相同的項將覆蓋 const merge = require('webpack-merge') // 引入開發環境和生產環境公共的配置 const baseWebpackConfig = require('./webpack.base.conf') // 引入copy-webpack-plugin模組 這個模組主要用於在webpack中拷貝檔案和資料夾 const CopyWebpackPlugin = require('copy-webpack-plugin') // 引入html-webpack-plugin外掛 這個外掛主要是用於基於模版生成html檔案的 const HtmlWebpackPlugin = require('html-webpack-plugin') // 引入extract-text-webpack-plugin外掛 這個外掛主要是用於將入口中所有的chunk,移到獨立的分離的css檔案中 const ExtractTextPlugin = require('extract-text-webpack-plugin') // 引入optimize-css-assets-webpack-plugin外掛 這個外掛主要是用於壓縮css模組的 const OptimizeCSSPlugin = require('optimize-css-assets-webpack-plugin') // 引入uglifyjs-webpack-plugin外掛 這個外掛主要是用於壓縮js檔案的 const UglifyJsPlugin = require('uglifyjs-webpack-plugin') // 引入用於生產環境的一些基本變數 const env = require('../config/prod.env') // 合併公共配置和生產環境獨有的配置並返回一個用於生產環境的webpack配置檔案 const webpackConfig = merge(baseWebpackConfig, { // 用於生產環境的一些loader配置 module: { // 樣式檔案的處理規則,對css/sass/scss等不同內容使用相應的styleLoaders // 由utils配置出各種型別的預處理語言所需要使用的loader,例如sass需要使用sass-loader rules: utils.styleLoaders({ sourceMap: config.build.productionSourceMap, // 在生產環境中使用extract選項,這樣就會把thunk中的css程式碼抽離到一份獨立的css檔案中去 extract: true, usePostCSS: true }) }, // 配置生產環境中使用的source map的形式。在這裡,生產環境使用的是#source map的形式 devtool: config.build.productionSourceMap ? config.build.devtool : false, output: { // build所產生的檔案的存放的資料夾地址 path: config.build.assetsRoot, // build之後的檔案的名稱 // 這裡[name]和[chunkhash]都是佔位符 // 其中[name]指的就是模組的名稱 // [chunkhash]chunk內容的hash字串,長度為20 filename: utils.assetsPath('js/[name].[chunkhash].js'), // [id]也是一個佔位符,表示的是模組識別符號(module identifier) chunkFilename: utils.assetsPath('js/[id].[chunkhash].js') }, plugins: [ // http://vuejs.github.io/vue-loader/en/workflow/production.html // 下面是利用DefinePlugin外掛,定義process.env環境變數為env new webpack.DefinePlugin({ 'process.env': env }), // 壓縮javascript的外掛 new UglifyJsPlugin({ uglifyOptions: { compress: { // 在刪除未使用的變數等時,顯示警告資訊,預設就是false warnings: false // 禁止顯示壓縮時候的警告資訊 } }, // 使用 source map 將錯誤資訊的位置對映到模組(這會減慢編譯的速度) // 而且這裡不能使用cheap-source-map sourceMap: config.build.productionSourceMap, // 使用多程序並行執行和檔案快取來提高構建速度 parallel: true }), // extract css into its own file // 提取css檔案到一個獨立的檔案中去 new ExtractTextPlugin({ // 提取之後css檔案存放的地方 // 其中[name]和[contenthash]都是佔位符 // [name]就是指模組的名稱 // [contenthash]根據提取檔案的內容生成的 hash filename: utils.assetsPath('css/[name].[contenthash].css'), // 從所有額外的 chunk(additional chunk) 提取css內容 // (預設情況下,它僅從初始chunk(initial chunk) 中提取) // 當使用 CommonsChunkPlugin 並且在公共 chunk 中有提取的 chunk(來自ExtractTextPlugin.extract)時 // 這個選項需要設定為true }), // Compress extracted CSS. We are using this plugin so that possible // duplicated CSS from different components can be deduped. // 使用這個外掛壓縮css,主要是因為,對於不同元件中相同的css可以剔除一部分 new OptimizeCSSPlugin({ // 這個選項的所有配置都會傳遞給cssProcessor // cssProcessor使用這些選項決定壓縮的行為 cssProcessorOptions: config.build.productionSourceMap // safe我不是很明白是什麼意思???求留言告知。。。 ? { safe: true, map: { inline: false } } : { safe: true } }), // generate dist index.html with correct asset hash for caching. // you can customize output by editing /index.html // see https://github.com/ampedandwired/html-webpack-plugin // 建立一個html檔案 new HtmlWebpackPlugin({ // 生成的檔案的名稱 filename: config.build.index, // 使用的模板的名稱 template: 'index.html', // 把script和link標籤放在body底部 inject: true, // 配置html的壓縮行為 minify: { removeComments: true, // 移除註釋 collapseWhitespace: true, // 去除空格和換行 removeAttributeQuotes: true // 儘可能移除屬性中的引號和空屬性 // more options: // https://github.com/kangax/html-minifier#options-quick-reference }, // necessary to consistently work with multiple chunks via CommonsChunkPlugin // 控制chunks的順序,這裡表示按照依賴關係進行排序 // 也可以是一個函式,自己定義排序規則 chunksSortMode: 'dependency' }), // keep module.id stable when vendor modules does not change // 根據模組的相對路徑生成一個四位數的hash作為模組id new webpack.HashedModuleIdsPlugin(), // enable scope hoisting // webpack2處理過的每一個模組都會使用一個函式進行包裹 // 這樣會帶來一個問題:降低瀏覽器中JS執行效率,這主要是閉包函式降低了JS引擎解析速度。 // webpack3中,通過下面這個外掛就能夠將一些有聯絡的模組, // 放到一個閉包函式裡面去,通過減少閉包函式數量從而加快JS的執行速度。 new webpack.optimize.ModuleConcatenationPlugin(), // split vendor js into its own file // 這個外掛用於提取多入口chunk的公共模組 // 通過將公共模組提取出來之後,最終合成的檔案能夠在最開始的時候載入一次 // 然後快取起來供後續使用,這會帶來速度上的提升。 new webpack.optimize.CommonsChunkPlugin({ // 這是 common chunk 的名稱 name: 'vendor', minChunks (module) { // any required modules inside node_modules are extracted to vendor // 把所有從mnode_modules中引入的檔案提取到vendor中 return ( module.resource && /\.js$/.test(module.resource) && module.resource.indexOf( path.join(__dirname, '../node_modules') ) === 0 ) } }), // extract webpack runtime and module manifest to its own file in order to // prevent vendor hash from being updated whenever app bundle is updated // 為了將專案中的第三方依賴程式碼抽離出來,官方文件上推薦使用這個外掛,當我們在專案裡實際使用之後, // 發現一旦更改了 app.js 內的程式碼,vendor.js 的 hash 也會改變,那麼下次上線時, // 使用者仍然需要重新下載 vendor.js 與 app.js——這樣就失去了快取的意義了。所以第二次new就是解決這個問題的 // 參考:https://github.com/DDFE/DDFE-blog/issues/10 new webpack.optimize.CommonsChunkPlugin({ name: 'manifest', minChunks: Infinity }), // This instance extracts shared chunks from code splitted chunks and bundles them // in a separate chunk, similar to the vendor chunk // see: https://webpack.js.org/plugins/commons-chunk-plugin/#extra-async-commons-chunk new webpack.optimize.CommonsChunkPlugin({ name: 'app', async: 'vendor-async', children: true, minChunks: 3 }), // copy custom static assets // 拷貝靜態資源到build資料夾中 new CopyWebpackPlugin([ { // 定義要拷貝的資源的源目錄 from: path.resolve(__dirname, '../static'), // 定義要拷貝的資源的目標目錄 to: config.build.assetsSubDirectory, // 忽略拷貝指定的檔案,可以使用模糊匹配 ignore: ['.*'] } ]) ] }) if (config.build.productionGzip) { // 如果開啟了生產環境的gzip const CompressionWebpackPlugin = require('compression-webpack-plugin') webpackConfig.plugins.push( new CompressionWebpackPlugin({ // 目標資源的名稱 // [path]會被替換成原資源路徑 // [query]會被替換成原查詢字串 asset: '[path].gz[query]', // gzip演算法 // 這個選項可以配置成zlib模組中的各個演算法 // 也可以是(buffer, cb) => cb(buffer) algorithm: 'gzip', // 處理所有匹配此正則表示式的資源 test: new RegExp( '\\.(' + config.build.productionGzipExtensions.join('|') + ')$' ), // 只處理比這個值大的資源 threshold: 10240, // 只有壓縮率比這個值小的資源才會被處理 minRatio: 0.8 }) ) } // 如果啟動了report,則通過外掛給出webpack構建打包後的產品檔案分析報告 if (config.build.bundleAnalyzerReport) { // 如果需要生成一分bundle報告,則需要使用下面的這個外掛 const BundleAnalyzerPlugin = require('webpack-bundle-analyzer').BundleAnalyzerPlugin webpackConfig.plugins.push(new BundleAnalyzerPlugin()) } module.exports = webpackConfig