【问题标题】:How to get Tree Shaking to work in Webpack 4 for React Library "material-ui"?如何让 Tree Shaking 在 Webpack 4 中为 React 库“material-ui”工作?
【发布时间】:2018-08-30 17:12:56
【问题描述】:

虽然我按照文档中解释的步骤(请参阅here)启用 Tree Shaking,但它似乎没有任何效果。我将Webpack 4ts-loader 一起用于TypeScript。有问题的图书馆是material-ui。在他们的文档(参见How to reduce the bundle size?)中,他们建议“直接从material-ui/ 导入以避免引入未使用的模块”,然后他们添加“这两个选项都应该是临时的,直到您向项目添加摇树功能。”。所以我认为 Tree Shaking 应该有一些效果。

要明确:他们建议像这样导入:

import RaisedButton from "material-ui/RaisedButton";

不是这样的:

import {RaisedButton} from "material-ui";

我做了什么:

  • 仅使用 ES2015 模块语法(即导入和导出)。
  • 在我的项目的package.json 文件中添加了一个"sideEffects":false 条目。并确保拼写正确。
  • mode: "production" 中运行 Webpack,Webpack 4 允许使用它而不是 UglifyJsPlugin(“从 webpack 4 开始,这也可以通过“模式”配置选项轻松切换,设置为“生产”。”)

结果:没有。没有缩小尺寸。所以也许我做错了什么?


对于基准测试爱好者:这就是单个 RaisedButton 在捆绑包大小方面的成本。没有缩小(即生产模式):

Initial (in mode "development"): 
1,63 MiB (No Material UI)

MuiThemeProvider
1,94 MiB -> +0,31 (`import {MuiThemeProvider} from "material-ui/styles";`)
1,92 MiB -> +0,29 (`import MuiThemeProvider from 'material-ui/styles/MuiThemeProvider';`)

RaisedButton
3,07 MiB -> +1,13 (`import {RaisedButton} from "material-ui";`)
2,03 MiB -> +0,09 (`import RaisedButton from "material-ui/RaisedButton";`)

并进行缩小(无压缩):

Initial (in mode "production"):
284 KiB (No Material UI)

MuiThemeProvider
371 KiB -> +087 (`import {MuiThemeProvider} from "material-ui/styles";`)
367 KiB -> +077 (`import MuiThemeProvider from 'material-ui/styles/MuiThemeProvider';`)

RaisedButton
705 KiB -> +338 (`import {RaisedButton} from "material-ui";`)
400 KiB -> +033 (`import RaisedButton from "material-ui/RaisedButton";`)

并启用 Tree Shaking:

705 KiB (`import {RaisedButton} from "material-ui";`)
400 KiB (`import RaisedButton from "material-ui/RaisedButton";`)

即:完全没有效果。

【问题讨论】:

  • 我遇到了同样的问题。见github.com/mui-org/material-ui/issues/11281;另请参阅github.com/mui-org/material-ui/issues/…中链接的问题
  • 借助我之前评论中的这些链接,我发现了我的问题(类似于你的问题?)。如果你使用 webpack 4.x,使用 babel,添加 "modules": false 到你的 babelrc env: "presets": [ ["env", { "modules": false }], "react", "stage-0" ] 如果你在你的 webpack.config.prod.js (或类似的)中添加 material-ui/es 的别名.. 像这样:``` resolve: { ... alias: { 'material-ui': 'material -ui/es' } ``` 你应该可以让 tree-shaking 工作了。
  • 导入 {RaisedButton} from "material-ui import RaisedButton from "material-ui/RaisedButton"; 之间的差异并不重要,当使用 es 模块和 tree-shaking 时。只有不同才重要如果 tree-shaking 在您的项目中实际上不起作用,如文档中所示:“如果您有 tree-shaking 工作,则使用它很好,但是,在构建链中不支持或配置 tree-shaking 的情况下” - @ 987654325@
  • 此外,使用 webpack-bundle-analyzer 非常有助于确定、可视化和优化包大小:npmjs.com/package/webpack-bundle-analyzer
  • 您可能还想阅读medium.com/@martin_hotell/… 在我的情况下,我们不使用打字稿,而是使用 babel。那里的文章暴露了限制并展示了一种解决方法,使用 babel(仍然用于类型检查的打字稿)并成功地摇树 lodash。希望这对您有所帮助。干杯。

标签: webpack material-ui


【解决方案1】:

正如@qx3 所写,我已经能够通过添加:

alias: { '@material-ui/core': '@material-ui/core/es' }

在我的 webpack 配置中。

注意“@”前缀和“/core”后缀以适应库的新命名。这个简单的小东西帮助我摆脱了一些字节,并使团队能够以完全符合 esm 的方式编写“@material-ui/core”导入。

【讨论】:

  • 将此行添加到 web pack 配置后,我遇到了这个错误:``` ./node_modules/@material-ui/core/es/TextField/TextField.js 中的错误 109:46 模块解析失败: Unexpected token (109:46) 您可能需要适当的加载程序来处理此文件类型,目前没有配置加载程序来处理此文件。见webpack.js.org/concepts#loaders | | if (label) { > const displayRequired = InputLabelProps?.required ??必需的; ```所以解决方案不起作用
猜你喜欢
  • 2019-01-28
  • 2019-02-14
  • 2019-02-08
  • 1970-01-01
  • 2018-05-19
  • 2021-11-18
  • 1970-01-01
  • 2020-05-19
  • 2020-06-04
相关资源
最近更新 更多