tree shaking 有效触发的前提是统一使用 es module 语法,禁用 commonjs;需避免动态导出、非字面量 default 导出,并声明副作用;团队须规范模块使用、命名导出、导出即使用,配合构建分析与审计保障效果。

Tree Shaking 有效触发的前提条件
Tree Shaking 不是自动生效的魔法,它依赖于 ES 模块(import/export)的静态结构。CommonJS(require/module.exports)在运行时才确定依赖关系,无法被 Rollup、Webpack 等工具静态分析,因此必须统一使用 ES Module 语法。
常见破坏 Tree Shaking 的写法:
-
导出对象后动态添加属性:如
export const utils = {}; utils.fn = () => {};—— 工具无法判断fn是否被引用 -
default 导出非字面量:如
export default Object.assign({}, a, b);—— 静态分析失败 -
副作用导入未声明:如
import './polyfill.js';(仅执行无导出),需在package.json中标记"sideEffects": false或显式列出有副作用的文件
团队代码规范核心条款
为保障 Tree Shaking 效果稳定,团队需约定以下硬性规则:
将一个或多个视频上传至YouTube。当用户想“上传到YouTube”“发YouTube”“批量上传”“upload to YouTube”“post videos to YouTube”或发布到YouTube时使用此技能。
-
禁止混用模块系统:项目内所有源码(含工具函数、组件、配置)必须使用
import/export,禁用require和module.exports -
命名导出优先,避免 default 导出:每个模块按功能拆分细粒度命名导出(如
export const debounce,export const throttle),便于按需引入;若必须用 default,确保其为纯对象/函数字面量 -
导出即使用,不预留“未来接口”:不导出未被当前项目任何地方 import 的符号;可借助 ESLint 插件
eslint-plugin-tree-shaking自动检测未使用导出 -
工具库封装需支持模块化消费:自研工具包发布时启用
exports字段(支持 Node.js 12+),提供esm入口,并在package.json中设置"type": "module"或明确"module"字段
构建与验证流程标准化
规范落地需配套可验证的工程实践:
-
构建产物分析常态化:CI 中集成
source-map-explorer或webpack-bundle-analyzer,对主包体积突增自动告警 -
启用严格模式检查:Webpack 配置中设置
optimization.usedExports: true(已默认开启),并开启devtool: 'source-map'方便溯源 -
测试用例覆盖导出路径:单元测试应包含对单个导出项的独立引入验证(如
import { throttle } from '@/utils'),确保该路径真实可达且无副作用 -
定期执行“摇树审计”:每季度运行
rollup --treeshake=verify或 Webpack 的stats.toJson({ usedExports: true }),生成未被引用的导出清单,推动清理
协作提示与常见误区提醒
开发者日常需注意的细节:
-
解构导入不等于安全:如
import { foo } from 'lib';能摇掉bar,但若'lib'内部foo依赖了未导出的副作用逻辑,仍可能保留整块模块 —— 关键看上游库是否自身支持 Tree Shaking -
Babel 转译可能破坏结构:启用
@babel/preset-env时需设modules: false,否则会把export编译成module.exports,直接废掉摇树能力 -
CSS / 图片等资源也适用:通过
import './style.css';引入样式时,若未在 JS 中实际调用对应组件,且 CSS 文件无全局副作用,配合sideEffects: false同样可被摇掉 - TypeScript 不影响摇树:TS 编译后的 JS 输出只要符合 ES Module 规范,类型注解本身不参与打包,无需特殊处理










