打开APP
userphoto
未登录

开通VIP,畅享免费电子书等14项超值服

开通VIP
webpack之tree shaking

什么是tree-shaking?

前端中的tree-shaking可以理解为通过工具"摇"我们的js文件,将其中用不到的代码"摇"掉,是一个性能优化的范畴。具体来说,在webpack项目中,
有一个入口文件,相当于一棵树的主干,入口文件有很多依赖的模块,相当于树枝。实际情况中,虽然依赖啦某个模块,但其实只使用其中的某些功能。通过
tree-shaking,将没有使用的模块摇掉,这样来达到删除无用代码的目的。

tree-shaking原理

tree-shaking原理,简单来说

  • tree shaking的本质是消除无用的Javascript代码
  • 因为ES6模块的出现,ES6模块依赖关系是确定的,和运行时的状态无关,可以进行可靠的静态分析

怎么使用tree-shaking?

  • 在webpackDemo/demo下新建一个文件tree-shaking,文件目录如下

  • index.js内容如下
import {add} from "./math.js"console.log(mathFn)function component(){    var element = document.createElement("pre");    element.innerHTML = [        "hello webpack",        "5 cubed is equal to "   add(5,6)    ].join("\n\n");    return element;}document.body.appendChild(component())
  • math.js内容如下
export function add(a,b){    console.log("add");    return a b;}export function minus(a,b){    console.log("minus")    return a-b}export function multiply(a,b){    console.log("mutiply");    return a*b;}export function divide(a,b){    console.log("divide");    return a/b;}
  • tree-shaking.js内容如下
const path = require("path");const HtmlWebpackPlugin = require("html-webpack-plugin");const {CleanWebpackPlugin} = require("clean-webpack-plugin");const webpack = require("webpack");module.exports = {    mode:"development",    entry:path.resolve(__dirname,"src/index.js"),    module:{        rules:[            {                test:/\.m?js$/,                exclude:/(node_modules|bower_components)/,                use:{                    loader:"babel-loader",                    options:{                        presets:["@babel/preset-env"],                        plugins:[                            "@babel/plugin-transform-runtime"                        ]                    }                }            }        ]    },    output:{        filename:"bundle.js",        path:path.resolve(__dirname,"dist")    },    plugins:[        new CleanWebpackPlugin(),        new HtmlWebpackPlugin(),//      new webpack.NamedModulesPlugin(),//      new webpack.HotModuleReplacementPlugin()    ],    devtool:"inline-source-map",//  devServer:{//      contentBase:"./dist",//      hot:true,//      inline:true//  }}
  • package.json 内容如下
{  "name": "webpackDevServer",  "sideEffects": false,  "version": "1.0.0",  "description": "",  "main": "index.js",  "scripts": {    "test": "echo \"Error: no test specified\" && exit 1",    "dev": "webpack-dev-server --config demo/webpack-dev-server/webpack-dev-server.js",    "server": "node demo/webpack-dev-middleware/server.js",    "hmr": "webpack-dev-server  --config demo/HMR/webpack.hmr.js",    "treeShaking:dev": "webpack-dev-server --config demo/tree-shaking/tree-shaking.js",    "treeShaking:build": "webpack  --config demo/tree-shaking/tree-shaking.js"  },  "keywords": [],  "author": "",  "license": "ISC",  "devDependencies": {    "@babel/core": "7.6.4",    "@babel/plugin-transform-runtime": "^7.6.2",    "@babel/preset-env": "^7.6.3",    "babel-loader": "8.0.6",    "clean-webpack-plugin": "3.0.0",    "css-loader": "3.2.0",    "express": "4.17.1",    "html-webpack-plugin": "3.2.0",    "style-loader": "1.0.0",    "webpack": "4.41.2",    "webpack-cli": "3.3.9",    "webpack-dev-middleware": "3.7.2",    "webpack-dev-server": "3.8.2"  }}
  • 执行 npm run treeShaking:build

执行结果如下


执行后我们可以看到bundle.js文件,可以发现math.js中所有的代码都被打包了,而我们只用了文件中的add函数,我们没用到的函数不想打包到文件,这时我们可以用到tree-shaking

  • 启用webpack
    当前项目中使用的是webpack4,讲mode设置为production即可开启tree shaking

关于side effects(副作用)

副作用是指除了函数返回值以外,任何在函数调用之外观察到的应用程序状态改变。副作用包括:

  • 改变了任何外部变量或对象属性(例如,全局变量,或者一个在父级函数作用域链上的变量)
  • 写日志
  • 在屏幕输出
  • 写文件
  • 发网络请求
  • 触发任何外部进程
  • 调用另一个有副作用的函数

tree shaking不能自动的识别那些代码属于side effects,因此手动指定这些代码非常重要,如果不指定可能会出现一些意想不到的问题

在webpack中,是通过packge.json的sideEffects属性来实现的
{
"name":"tree-shaking",
"sideEffects":false
}

如果所有代码都包含副作用,我们可以简单地将属性标记为false,并告知webpack,他可以安全地删除未用到的export导出

如果你的代码确实有一些副作用,那么可以改为提供一个数组

{
"name": "tree-shaking",
"sideEffects": [
"./src/common/polyfill.js"
]
}

总结

  • tree shaking 不支持动态导入(如CommonJS的require()语法),只支持纯静态的导入(ES6的import/export)
  • webpack中可以在项目package.json中添加一个"sideEffects"属性,手动指定有副作用的脚本

将mode修改,在package.json里设置sideEffects:false结果如下

我们可以看出使用了tree shaking后,代码体积变小,并且我们引用的math.js函数add被转换,其他未引用的代码并没有出现

来源:https://www.icode9.com/content-4-663051.html
本站仅提供存储服务,所有内容均由用户发布,如发现有害或侵权内容,请点击举报
打开APP,阅读全文并永久保存 查看更多类似文章
猜你喜欢
类似文章
【热】打开小程序,算一算2024你的财运
我从 Vuejs 中学到了什么
超详细使用webpack4.x搭建标准前端项目
Vue2.0 新手完全填坑攻略
Webpack+React+ES6开发模式入门指南
webpack的使用方法,超详细的学习笔记
webpack的入门实践,看这篇就够了
更多类似文章 >>
生活服务
热点新闻
分享 收藏 导长图 关注 下载文章
绑定账号成功
后续可登录账号畅享VIP特权!
如果VIP功能使用有故障,
可点击这里联系客服!

联系客服