Skip to main content

Webpack快速构建SPA应用🤔

🤪 基本操作

  1. 初始化项目文件package.json生成

    yarn init

  2. 安装webpack

yarn add webpack -D

  1. 测试你的webpack建立文件夹./src/index.js ,运行

webpack

  1. 包管理和直接运行webpack区别

  2. 包管理yarn npm,提示安装webpack-cli

"scripts": {
"dev": "webpack --mode development",
"prod": "webpack --mode production"
},

🤪 JS的treeShaking

让development也体验到treeShaking

// ./src/utils/tool.js
const isObj = (obj) => {
console.log("coming in obj");
};
const isArray = () => {
console.log("coming in array");
};
export {
isObj,
isArray
};
// ./src/index.js
import { isObj } from "./utils/tool";
console.log("hello");
isObj();

webpack --mode development 看dist被全部导出来了;

webpack --mode production 实现了js的treeShaking,没有用到的js函数,没有写入dist中

development 开启JS tree shaking

// webpack.config.js
optimization: {
usedExports: true
}

会标记出/* unused harmony export isArray */

Bable

如果让ES6转变成ES5怎么处理呢?

首先yarn add babel-loader -D

rules: [{
test: /\.js$/,
exclude: /node_modules/,
use: ['babel-loader']
}]

❌:Error: Cannot find module '@babel/core'

安装解释JavaScript: yarn add @babel/core -D

根目录创建 .babelrc

{
"presets": [
["@babel/preset-env", {
"useBuiltIns": "usage", // "entry" or "usage"
"corejs": 3
}]

],
"plugins": []
}

安装:yarn add @babel/preset-env -D

// ./src/index.js
const promise = new Promise((resolve, reject) => {});
console.log(promise);

安装:yarn add core-js -D

🤪 CSS的treeShaking

webpack处理css

/* ./src/assets/css/test.css */
.test{
--fontColor: yellowgreen;
color: var(--fontColor);
}
./src/index.js
import "./assets/css/test.css";

运行yarn dev

报错❌:You may need an appropriate loader to handle this file type, currently no loaders are configured to process this file.

缺少解释CSS的loader

yarn add css-loader -D

yarn add style-loader -D

module: {
rules: [{
test: /\.css$/,
use: [
'style-loader',
{
loader: 'css-loader',
options: {
modules: true,
},
}
],
}]
},

发现 html 的 class 的文件一堆哈希

modules: {
localIdentName: "[name]-[hash:5]"
}

又一个缺点css在html文件夹里,怎样才能把css抽离出来?

CSS的分离文件

yarn add mini-css-extract-plugin -D

mini-css-extract-plugin就不再用style-loader

module: {
rules: [{
test: /\.css$/,
use: [
// 'style-loader',
MiniCssExtractPlugin.loader,
{
loader: 'css-loader',
options: { importLoaders: 1 }
}
],
}]
},
plugins: [
new MiniCssExtractPlugin({
filename: '[name].css',
chunkFilename: '[id].css',
}),
]
import "./assets/css/test.css";
<link rel="stylesheet" href="./styles.css">
<div id="app">
<h1 class="test">TEST</h1>
</div>

发现生成一个style.css,先手动引入index.html

CSS tree Shaking

yarn add purgecss-webpack-plugin -D

🤪 development & production

entry & output

entry: path.resolve(__dirname, 'src/index.js'),
output: {
path: path.join(__dirname, "./dist"),
filename: "scripts/[name].bundule.js",
chunkFilename: 'scripts/[id].chunk.js',
publicPath: "/"
},

yarn add clean-webpack-plugin -D

环境断言

yarn add yargs-parser -D

const { mode } = require('yargs-parser')(process.argv.slice(2));
console.log("🤪🤪🤪coming in webpack config", mode);

容错

const _mode = mode || "development";
const _modeflag = (_mode == "production" ? true : false);
new MiniCssExtractPlugin({
filename: _modeflag ? 'styles/[name].[hash:5].css' : 'styles/[name].css',
chunkFilename: _modeflag ? 'styles/[id].[hash:5].css' : 'styles/[id].css',
}),

development & production分离

yarn add webpack-merge -D

const { merge } = require('webpack-merge');
const _mergeConfig = require(`./config/webpack.${_mode}.js`);

const webpackConfig = {};
//_modeflag在MiniCssExtractPlugin判断生成不同的文件夹
module.exports = merge(_mergeConfig, webpackConfig);
// ./config/webpack.development.js
// ./config/webpack.production.js
module.exports = {}

🤪 html-webpack-plugin

yarn add html-webpack-plugin -D

const HtmlWebpackPlugin = require('html-webpack-plugin');
module.exports = {
plugins: [
new HtmlWebpackPlugin({
title: 'Webpack构建SPA应用',
filename: 'index.html',
template: resolve(__dirname, '../src/index-dev.html'),
favicon: resolve(__dirname, '../favicon.ico')
}),
]
}

🤪 devServer

yarn add webpack-dev-server -D

devServer:{}
"dev": "webpack serve --mode development"

🤪 React

react-dom

yarn add react react-dom

{
test: /\.(js|jsx)$/,
exclude: /node_modules/,
use: ['babel-loader']
}

yarn add @babel/preset-react -D

{
"presets": [
// ["@babel/preset-env", {
// "useBuiltIns": "usage", // "entry" or "usage"
// "corejs": 3
// }]
"@babel/preset-react"
],
"plugins": []
}
// ./src/index.jsx
import React from 'react';
import ReactDOM from 'react-dom';
ReactDOM.render(<h1>Webpack SPA React</h1>, document.getElementById("root"));

别忘了入口文件哦换成jsx

react-router-dom

==待更新==

🤪 小小优化

CDN

./webpack.config.js  
externals: {
react: 'React',
'react-dom': 'ReactDOM'
},
<script src="https://cdn.staticfile.org/react/17.0.2/umd/react.development.js"></script>
<script src="https://cdn.staticfile.org/react-dom/17.0.2/umd/react-dom.development.js"></script>

webpack-build-notifier

yarn add webpack-build-notifier -D

const WebpackBuildNotifierPlugin = require("webpack-build-notifier");
new WebpackBuildNotifierPlugin({
title: "🤔 Webpack",
logo: resolve(__dirname, "../favicon.ico"),
suppressSuccess: true
}),

friendly-errors-webpack-plugin

yarn add friendly-errors-webpack-plugin -D

const FriendlyErrorsPlugin = require("friendly-errors-webpack-plugin");
new FriendlyErrorsPlugin({
compilationSuccessInfo: {
messages: ['You application is running success!!! http://localhost:8080'],
notes: ['']
},
onErrors: function (severity, errors) {

},
clearConsole: true,
additionalFormatters: [],
additionalTransformers: []
})

webpackbar

yarn add webpackbar -D

const WebpackBar = require('webpackbar');
new WebpackBar()

splitChunks 分包

==待更新==