階段1-第三章-webpack-高階配置(一)
阿新 • • 發佈:2019-08-12
1.HTML 中img標籤的圖片資源處理
html-withimg-loader
只要在html中正常引用圖片即可,webpack會找到對應的資源打包,html裡的img標籤的路徑資源打包,並且把資源重新命名,使用的是url的圖片配置、
- live-server 在當前資料夾起服務
2.多頁面應用的打包:
webpack.config.js const HtmlWebpackPlugin = require('html-webpack-plugin'); module.exports={ // 1.修改為多入口 entry:{ index:'./src/index.js', other:'./src/other.js' }, output:{ path:path.resolve('/dist'), // 2.多入口無法對應一個固定的出口,所以修改filename為[name]變數 filename:[name].js //[name] output 這裡可以根據傳入的name 來輸出對應的檔名,index.js和other.js }, plugin:[ // 根目錄下面的index.html是根據html-webpack-plugin 外掛生成的。 //根據index.html templare 生成的filename index.html // 3.如果用了html外掛,需要手動配置多入口對應的html檔案,將制定其對應的輸出檔案 new HtmlWebpackPlugin({ filename:'index.html', template:'./src/index.html', chunks:['index','main'] // 只引入要新增的chunks }), new HtmlWebpackPlugin({ filename:'other.html', template:'./src/other.html', chunks:['other'] }) ] }
3. 第三方庫的兩種引入方式
// 可以掛載多個全域性變數
可以通過 expose-loader 進行全域性變數的注入,同時也可以使用內建外掛webpack.ProvidePlugin 對每個模組的閉包空間,注入一個變數,制動載入模組,而不用匯出import 或 require
expose-loader 全域性變數 // 通常和第三方庫結合使用時會用到,因為第三方庫回去尋找全域性jquery變數
npm i expose-loader -D
webpack.ProvidePlugin
4.development和production不同配置檔案的打包
webpack-merge npm i webpack-merge -D webpack.base.js webapck.prod.js // 優化配置,程式碼拆分,程式碼壓縮,加密 webpack.dev.js 步驟如下: - 將開發環境和生產環境公用的配置放入base中,不同的配置各自放入prod和dev中 - 然後在dev和prod中使用webpack-merge 把自己的配置與base的配置進行合併並匯出 - 將 package.json中的指令碼引數進行修改,通過--config手動指定特定的配置檔案
webpack.dev.js
const merge = require('webpack-merge'); const baseConfig = require('./webpack.base.js') module.exports = merge(baseConfig,{ mode:'developlment' devServer:{ open:true, hot: true, compress: true, port: 3000, proxy:{ '/api': { target: "http://localhost:9999", pathRewrite: { // 轉發請求時不會攜帶 '/api' // 實際請求的是http://localhost:9999/getUserInfo '^/api': '' } } } } })
package.json
{
"script":{
"test": 'echo',
"buildcustom":"webpack --config webpack.custom.config.js",
"build":"webpack --config ./build/webapck.prod.js",
"dev":"webpack-dev-server --config ./build/webpack.dev.js",
"server": "node server.js",
"start": "live-server ./dist" //用live-server 開啟dist資料夾,啟動小型伺服器
}
}
定義build資料夾,將 webpack.base.js, webpack.prod.js, webpack.dev.js 放入build資料夾
此時在output路徑拼接需要使用:
output:{
//相對路徑都是相對的專案根目錄,絕對路徑是當前檔案所在的的絕對路徑記得往上翻一層
path:path.resolve(__dirname,'..','./dist/')
},
plugins:[
new CopyWebpackPlugin({
from: path.join(__dirname,'..','assets'),
to: 'assets'
})
]
5. 定義環境變數
webpack 內建外掛 webpack.DefinePlugin({})
DefinePlugin 會解析定義的環境變量表達式,這裡的值會當成變數來處理
此環境變數都可以在src打包的資料夾下面使用
let host = 'http://192.168.1.22:8080'
if(is_dev){
host = 'www.newbaker.cn:9999'
}
6. 使用devServer 解決跨越問題
- 由於開發時會用到webpack-dev-server ,所以一定會產生跨域問題
- jsonp (淘汰)
- cors 跨域資源共享
- http proxy
http代理
- 其原理就是將所有請求發給devServer,再由devServer伺服器做一次轉發,傳送給資料介面伺服器;
- 由於ajax是傳送給devServer伺服器的,所以不存在跨域,而devServer是用node平臺傳送的http請求,自然也不涉及跨域問題
node中使用CORS:
npm i cors --save-dev
app.js
const express = require('express')
const app = express()
const cors = require('cors') //加上了響應頭 responese Headersd Access-Control-Allow-Origin: *
app.use(cors())
app.get('/api/getUserInfo',(req,res) => {
res.send({
name:'wjx',
age: 18
})
})
app.listen(9999, () => {
console.log('http://localhost:9999')
})
7 HMR 熱更新
hot module reload // 不適用於生產環境,只是在開發環境
module.hot.accept('./hotModule.js',()=>{
// import 和 export 必須在頂級作用域使用
var str = require('./hotModule.js)
})
以上用到的配置webpack.config.js
const CleanWebpackPlugin = require('clean-webpack-plugin')
const CopyWebpackPlugin = require('copy-webpack-plugin')
const webpack = require('webpack')
const path = require('path')
module.exports={
entry: './src/main.js',
output:{
//必須為絕對路徑
//path.resolve() 解析當前路徑的絕對路徑
// path.join(__dirname,'./dist/')
path: path.resolve("./dist/"),
filename: 'bundle.js'
},
mode:'development' //不設定預設為production ,
// watch: true, //開啟監視模式,自動編譯,生成輸出檔案
devServer:{
open: true,
port: 5000,
hot: ture,
compress: true,
contentBase: '/src',
},
plugins:[
//外掛一般引入進來是個建構函式
//根據模板'/src/indtx.html'生成檔案'index.html'
new HtmlWebpackPlugin({
filename:'index',
template:'./src/index.html'
}),
new CleanWebpackPlugin(),
new CopyWebpackPlugin([{
from: path.join(__dirname,'assets'),
to:'assets'
},
{
from: path.join(__dirname,'image'),
to:'image'
}
]),
new webpack.BannerPlugin('可以為每個chunk檔案頭部新增banner'),
new webpack.ProvidePlugin({ // 內建外掛,在每個模組內部掛載一個jQuery
$:'jquery',
jQuery:'jquery'
}),
new webpack.DefinePlugin({
IS_DEV: 'true',
test1: '"1+1"' //這裡的值會當成變數來處理,所以裡面要用“” 拼接
})
],
module:{
rules:[
{
test:/\.css$/,
// webapck 讀取loader時 是從左到右讀取,會將css檔案先交給最右側的loader
// loader的執行順序是從右到左以管道的方式鏈式呼叫
// css-loader:解析css,使其支援css語法格式
// style-loader: 將解析出來的結果放到 html中,使其生效
use:['style-loader','css-loader']
},
{
test:/\.less$/,
//less-loader 只是將less檔案轉成css語法
use:['style-loader','css-loader','less-loader']
},
{
test:/\.s(a|c)ss$/,
use:['style-loader','css-loader','sass-loader']
},
{
test:/\.jpg|jpeg|png|gif|bmp$/,
use:['file-loader']
},
{
test:/\.(woff|woff2|eot|svg|ttf)$/,
use:['file-loader']
},
{
test:/\.(jpg|jpeg|png|gif|bmp)$/,
use:{
loader:'url-loader',
options:{
/* url-loader功能*/ limit:5*1024, //5kb 如果圖片大小 小於5kb直接轉成base64
/* file-loader功能*/ outputPath:'images',
/* file-loader功能*/ name:[name]-aaa[hash:4].[ext] //ext副檔名 -中間可以加常量,hash:4 保留4位hash值
}
}
},
{
test:/\.js$/,
use:{
loader:'babel-loader',
options:[
presets:['@babel/env'],
plugins:[
'@babel/plugin-proposal-class-properties',
'@babel/plugin-transform-runtime'
]
]
},
exclude:/node_modules/
},
{
test:/\.(html|htm)$/i,
user{
loader:'html-withimg-loader'
}
},
{
// 用於解析JQuery模組的絕對路徑
test:require.resolve('jquery'), // node_modules/jquery/pacakge.json > main
use:{
loader:'expose-loader',
options: '$' // 將引入的jquery掛載到了全域性$
}
}
]
},
devtools:'cheap-module-eval-sourc