十一、1.打包多页应用
- 文件 other.js home.js other.html home.html
- 安装包:
yarn add webpack webpack-cli html-webpack-plugin -D
webpack.config.js
let path = require('path');
let HtmlWebpackPlugin = require('html-webpack-plugin');
module.exports = {
mode: 'development',
entry: {
home: './src/home.js',
other: './src/other.js'
},
output: {
filename: '[name].[hash].js',
path: path.resolve(__dirname, 'dist')
},
plugins: [
new HtmlWebpackPlugin({
template: './src/home.html',
filename: 'home.html',
chunks:['home']
}),
new HtmlWebpackPlugin({
template: './src/other.html',
filename: 'other.html',
chunks:['other','home']
})
]
}
十二、2.配置source-map
- 高级语法转为低级语法,使用babel
2.安装包: @babel/core @babel/preset-env babel-loader
module:{
rules: [
{
test: /\.js$/,
use:{
loader: 'babel-loader',
options:{
presets: ['@babel/preset-env']
}
}
}
]
},
// 1) 源码映射,会单独生成一个source-map映射文件,出错后会标识当前报错的行和列,特点大和全
devtool: 'source-map', // 增加映射文件,方便调试代码
// 2)不会生成单独的映射文件,但报错后会显示行和列
// devtool: 'eval-source-map',
// 3)不会显示行和列,但会生成一个单独的映射文件
// devtool: 'cheap-module-source-map', // 生成后可以保留映射文件
// 4)不会生成单独的映射文件,会集成在打包的文件中,报错会显示行和列
// devtool: 'cheap-module-eval-source-map',
十三、3.watch的用法
- 自动打包
watch: true,
watchOptions:{ // 监控选项
poll: 1000, // 每秒询问是否更新文件
aggregateTimeout: 500, // 防抖 输入代码时
ignored: /node_moudules/ // 不监控文件
},
十四、4.webpack小插件应用
- 安装包:clean-webpack-plugin copy-webpack-plugin
- cleanWebpackPlugin copyWebpackPlugin bannerPlugin(内置)
- 每次打包删除的文件 new cleanWebpackPlugin('./dist')
- 把文件拷贝到打包文件 new copyWebpackPlugin([from: 'doc',to:'./'])
- 把版权声明打包每个文件的头部 webpack.BannerPlugin('make 2019 by kft')
let path = require('path');
const { CleanWebpackPlugin } = require('clean-webpack-plugin');
let copyWebpackPlugin = require('copy-webpack-plugin');
let HtmlWebpackPlugin = require('html-webpack-plugin');
let webpack = require('webpack');
module.exports = {
mode: 'production',
entry: './src/index.js',
output: {
filename: '[name].[hash].js',
path: path.resolve(__dirname, 'dist')
},
devtool: 'source-map', // 增加映射文件,方便调试代码
module:{
rules: [
{
test: /\.js$/,
use:{
loader: 'babel-loader',
options:{
presets: ['@babel/preset-env']
}
}
}
]
},
plugins: [
new CleanWebpackPlugin(),
new copyWebpackPlugin([{ from: 'doc', to: './' }]),
new webpack.BannerPlugin('make 2019 by kft'),
new HtmlWebpackPlugin({
template: './src/index.html',
filename: 'index.html',
}),
]
}
十五、5.webpack跨域问题
- server.js
let express = require('express') ;
let app = express();
app.get('/user',function(req,res){
console.log('/api/user');
res.json({namae:'kft'});
})
app.listen(3000,function(){
console.log(3000);
})
- src/index.js
let xhr = new XMLHttpRequest();
xhr.open('GET', '/user', true);
xhr.onload = function () {
console.log(xhr.response)
}
xhr.send();
- http-proxy 代理服务器
devServer: {
// 1)代理服务器
proxy:{ // 直接代理
'/api': 'http://localhost:3000'
}
// proxy:{
// '/api': { // 重写的方式,把请求代理到express服务器上
// target: 'http://localhost:3000',
// pathRewrite: {'/api':''}
// }
// }
},
- 模拟假数据
devServer: {
// 2)模拟假数据
before(app){
app.get('/user',(req,res)=>{
res.json({name:'珠峰架构'})
})
}
},
- 前后端启动到一个源域名下
- 安装包 webpack-dev-middleware 中间件
server.js
let express = require('express') ;
let app = express();
let webpack = require('webpack');
// 中间件
let middle = require('webpack-dev-middleware');
let config = require('./webpack.config.js');
let compiler = webpack(config);
app.use(middle(compiler));
app.get('/user',function(req,res){
console.log('/api/user');
res.json({namae:'kft'});
})
app.listen(3000,function(){
console.log(3000);
})
十六、6.resolve属性的配置
- 解析 resolve
- 强制当前目录查找node_modules, modules
- 配置别名,alias
- 优先读取的文件:mianFields
- 寻找扩展名: extensions
- webpack.config.js
resolve:{ // 解析 第三方包 common
modules: [path.resolve('node_modules')],
// alias: { // 别名
// bootstrap: 'bootstrap/dist/css/bootstrap.css',
// },
// mainFields: ['style','main'], // 先找style,再找main
// mainFiles: [], // 入口文件的名字,默认index.js
extensions:['.js','.css','.json'], // 扩展名依次寻找.js -> .css -> .json
},
十七、7.定义环境变量
- webpack.config.js
let webpack = require('webpack');
new webpack.DefinePlugin({
// ENV: "'env'",
ENV: JSON.stringify('production'),
FLAG: true,
EXPRESSION: '1+1'
})
- 在文件中直接读取
let url = '';
if(ENV==='env'){
url = 'http://localhost:3000'
}else{
url = 'http://localhost:8080'
}
console.log(url); // http://localhost:8080
console.log(typeof FLAG); // boolean
console.log(EXPRESSION); // 2
十八、8.区分不同环境
- 开发:webpack.dev.js,生产:webpack.prod.js,公共配置:webpack.base.js
- 安装包: webpack-merge
- webpack.dev.js 启动
$ npx webpack --config webpack.dev.js 或者 $ npm run build -- --config webpack.dev.js
let smart = require('webpack-merge');
let base = require('./webpack.base');
module.exports = smart(base, {
mode: 'development',
devServer: {
},
devtool: 'source-map',
})
- webpack.prod.js 启动
$ npx webpack --config webpack.prod.js 或者 $ npm run build -- --config webpack.prod.js
let smart = require('webpack-merge');
let base = require('./webpack.base');
const { CleanWebpackPlugin } = require('clean-webpack-plugin');
module.exports = smart(base, {
mode: 'production',
// optimization: {
// minimize: [
// ]
// },
plugins:[
new CleanWebpackPlugin(),
]
})
webpack.config.js
let path = require('path');
// const { CleanWebpackPlugin } = require('clean-webpack-plugin');
// let copyWebpackPlugin = require('copy-webpack-plugin');
let HtmlWebpackPlugin = require('html-webpack-plugin');
let webpack = require('webpack');
let webpackDevMiddleware = require('webpack-dev-middleware');
module.exports = {
mode: 'development',
entry: './src/index.js',
output: {
filename: '[name].[hash].js',
path: path.resolve(__dirname, 'dist')
},
devtool: 'source-map', // 增加映射文件,方便调试代码
module:{
rules: [
{
test: /\.css$/,
use:['style-loader','css-loader']
},
{
test: /\.js$/,
use:{
loader: 'babel-loader',
options:{
presets: ['@babel/preset-env']
}
}
}
]
},
// watch: true,
// watchOptions:{ // 监控选项
// poll: 1000, // 每秒询问是否更新文件
// aggregateTimeout: 500, // 防抖 输入代码时
// ignored: /node_moudules/ // 不监控文件
// },
devServer: {
// // 1)代理服务器
// proxy:{ // 直接代理
// '/api': 'http://localhost:3000'
// }
// proxy:{
// '/api': { // 重写的方式,把请求代理到express服务器上
// target: 'http://localhost:3000',
// pathRewrite: {'/api':''}
// }
// }
// // 2)模拟假数据
// before(app){
// app.get('/user',(req,res)=>{
// res.json({name:'珠峰架构'})
// })
// }
// // 3)前后端启动到一个源域名下
},
resolve:{ // 解析 第三方包 common
modules: [path.resolve('node_modules')],
// alias: { // 别名
// bootstrap: 'bootstrap/dist/css/bootstrap.css',
// },
// mainFields: ['style','main'], // 先找style,再找main
// mainFiles: [], // 入口文件的名字,默认index.js
extensions:['.js','.css','.json'], // 扩展名依次寻找.js -> .css -> .json
},
plugins: [
// new CleanWebpackPlugin(),
// new copyWebpackPlugin([{ from: 'doc', to: './' }]),
// new webpack.BannerPlugin('make 2019 by kft'),
new HtmlWebpackPlugin({
template: './src/index.html',
filename: 'index.html',
}),
// 定义环境变量
new webpack.DefinePlugin({
// ENV: "'env'",
ENV: JSON.stringify('production'),
FLAG: true,
EXPRESSION: '1+1'
})
]
}
// // 3)前后端启动到一个源域名下 server.js
// let express = require('express') ;
// let app = express();
// let webpack = require('webpack');
// // 中间件
// let middle = require('webpack-dev-middleware');
// let config = require('./webpack.config.js');
// let compiler = webpack(config);
// app.use(middle(compiler));
// app.get('/user',function(req,res){
// console.log('/api/user');
// res.json({namae:'kft'});
// })
// app.listen(3000,function(){
// console.log(3000);
// })
// // src/index.js
// let xhr = new XMLHttpRequest();
// xhr.open('GET', '/user', true);
// xhr.onload = function () {
// console.log(xhr.response)
// }
// xhr.send();
package.json
{
"name": "webpack-dev-2",
"version": "1.0.0",
"main": "index.js",
"license": "MIT",
"scripts": {
"build": "webpack --config webpack.config.js",
"dev": "webpack-dev-server"
},
"devDependencies": {
"@babel/core": "^7.4.5",
"@babel/preset-env": "^7.4.5",
"babel-loader": "^8.0.6",
"bootstrap": "^4.3.1",
"clean-webpack-plugin": "^3.0.0",
"copy-webpack-plugin": "^5.0.3",
"css-loader": "^3.0.0",
"html-webpack-plugin": "^3.2.0",
"style-loader": "^0.23.1",
"webpack": "^4.35.2",
"webpack-cli": "^3.3.5",
"webpack-dev-middleware": "^3.7.0",
"webpack-dev-server": "^3.7.2",
"webpack-merge": "^4.2.1"
},
"dependencies": {
"express": "^4.17.1"
}
}