Tree-Shaking 相关笔记
今天同事做完项目改造 Code Review
时,对 api
的导出形式有了点小讨论,于是今天的学习就有了
改造前
js
export const get1 = () => {}
export const get2 = () => {}
export const get3 = () => {}
改造后
js
export default {
get1() {},
get2() {},
get3() {}
}
当看完改造前后的代码我提出了异议:改造后的代码不利于 webpack
做 tree-shaking
,但是代码已经改动了,都改成了这样的调用方式
js
import api from 'api'
api.get1().then((res) => {})
于是喜欢偷懒的我提出使用模块整体加载语法来减少代码改动
js
import * as api from 'api'
当提出这个解决方案后,我就给自己提了一个问: 使用模块整体加载语法会不会影响 webpack
做 tree-shaking
,然后我进行打包实验了一番
先定义一个 api
模块
js
export const get1 = () => {}
export const get2 = () => {}
export const get3 = () => {}
然后通过模块整体加载语法引入 api
模块
js
import * as api from 'api'
api.get1()
通过打包后发现模块整体加载语法不会影响 tree-shaking
,我们没有用到的 get2
get3
都被移除了
总所周知 es6
在对象上扩展了属性名表达式,如果我们通过这种方式来调用 api
模块的方法会怎么样呢(我当时想着,这么简单的字符串拼接应该不会影响 tree-shaking
的 )
js
import * as api from 'api'
const get = 'get'
api[get + '1']()
再次打包分析,发现 tree-shaking
失效了,get1
get2
get3
都还在代码里面
结论
- 术语版:当你使用模块整体加载语法不使用属性名表达式时不影响
tree-shaking
- 通俗版:当你
import * as xx from 'xxx'
引入一个模块,使用字符串拼接的形式调用xx
的方法时是不可以去除没有用到的代码(今天有人说我被 997 搞的表达能力不行了)