美文网首页
使用Webpack优化你的第三方库

使用Webpack优化你的第三方库

作者: weihongyu12 | 来源:发表于2019-07-26 17:21 被阅读0次

    本文翻译自GoogleChromeLabs

    在webpack项目中使用了第三方库?使用这些方法可以缩小bundle!

    async

    async是一组用于处理异步函数的实用程序。

    通常,您应该使用async-es。它随ES模块一起提供,并且更适合webpack打包。

    尽管如此,即使更喜欢使用async,对于优化列表,请参阅async-es部分。

    async-es

    async-es是一组用于处理异步函数的实用程序。它与async相同,但它更适合webpack打包。

    使用babel-plugin-lodash删除未使用的方法

    如果你使用async-es作为单个导入,你将整个库打包到应用程序中 —— 即使你只使用它的几个方法:

    // 您只使用`async.map`,但整个库被打包
    import async from 'async-es';
    
    async.map(['file1', 'file2', 'file3'], fs.stat, function(err, results) {
      console.log(results);
    });
    

    使用babel-plugin-lodash只选择你需要的async-es方法:

    // 应用Babel之前
    import async from 'async-es';
    
    async.map(['file1', 'file2', 'file3'], fs.stat, function(err, results) {
      console.log(results);
    });
    

    // 应用Babel之后
    import _map from 'async-es/map';
    
    _map(['file1', 'file2', 'file3'], fs.stat, function(err, results) {
      console.log(results);
    });
    

    启用此插件,如下所示:

    // .babelrc
    {
      "plugins": [["lodash", { "id": ["async-es"] }]],
    }
    

    babel-polyfill

    babel-polyfill是一个Babel的包,它加载了core-js和一个自定义的再生器运行时。

    有关优化列表,请参阅core-js部分。

    core-js

    core-js是一套用于ES5和ES2015+的polyfill。

    使用babel-preset-env删除不必要的polyfill

    如果使用Babel和babel-preset-env编译代码,请添加useBuiltIns: true选项。此选项将Babel配置为仅包含目标浏览器所必需的polyfill。例如,如果您将应用程序定位为支持Internet Explorer 11:

    // .babelrc
    {
      "presets": [
        [
          "env",
          {
            "targets": {
              "browsers": ["last 2 versions", "ie >= 11"]
            }
          }
        ]
      ]
    }
    

    启用useBuiltIns: true将删除Internet Explorer 11已支持的所有功能(例如Object.createObject.keys等)的polyfill。

    将非转换代码发送到现代浏览器

    所有支持<script type ="module">的浏览器也支持现代JS功能,如async/await,箭头函数和类。使用此功能构建bundle的两个版本,并使现代浏览器仅加载现代代码。有关指南,请参阅Philip Walton的文章

    date-fns

    date-fns是一个日期实用程序库。

    启用babel-plugin-date-fns

    babel-plugin-date-fns使用特定日期函数函数的导入替换date-fns的完整导入:

    import { format } from 'date-fns';
    format(new Date(2014, 1, 11), 'MM/DD/YYYY');
    

    import _format from 'date-fns/format';
    _format(new Date(2014, 1, 11), 'MM/DD/YYYY');
    

    lodash

    Lodash是一个实用程序库。

    启用babel-plugin-lodash

    babel-plugin-lodash通过导入特定的Lodash功能取代了完整的Lodash导入:

    import _ from 'lodash';
    _.map([1, 2, 3], i => i + 1);
    

    import _map from 'lodash/map';
    _map([1, 2, 3], i => i + 1);
    

    注意:该插件不适用于方法链 - 比如这样的代码不会被优化。

    _([1, 2, 3]).map(i => i + 1).value();
    

    lodash-es别名为lodash

    一些依赖项可能使用lodash-es而不是lodash。如果是这样的话,Lodash将打包两次。

    为避免这种情况,请将lodash-es包别名为lodash

    // webpack.config.js
    module.exports = {
      resolve: {
        alias: {
          'lodash-es': 'lodash',
        },
      },
    };
    

    启用lodash-webpack-plugin

    lodash-webpack-plugin剥离了你不需要的Lodash功能部分。例如,如果您使用_.get()但不需要深层路径支持,则此插件可以删除它。将其添加到您的webpack配置中以使打包更小。

    请谨慎使用该插件。 默认设置会删除许多功能,您的应用可能会使用其中一些功能。

    lodash-es

    lodash-es是Lodash的ES模块。

    有关优化列表,请参阅lodash部分⤴。

    moment

    Moment.js是一个处理日期的库。

    使用moment-locales-webpack-plugin删除未使用的语言

    默认情况下,Moment.js附带160多KB压缩后的本地化文件。如果您的应用程序仅提供几种语言,则不需要所有这些文件。使用moment-locales-webpack-plugin删除未使用的语言。

    请谨慎使用该插件。 默认设置删除所有区域设置;如果您使用其中一些,这可能会破坏您的应用。

    react

    React是一个用于构建用户界面的库。

    删除生产中的propTypes声明

    React不会在生产中执行propTypes检查,但propTypes声明仍然占用了bundle的一部分。 使用babel-plugin-transform-react-remove-prop-types从构建过程中删除它们。

    迁移到另一个类似React的库

    React的替代品具有类似的API,具有更小的尺寸或更高的性能,但缺少一些功能(例如,Fragments, Portals或合成事件)。

    • Preact | 最小的React替代方案(preact@8.3.1 + preact-compat@3.18.3 7.6 kB gzipped; react@16.4.0 + react-dom@16.4.0 31.4 kB gzipped)| 没有合成事件| IE8支持polyfill

    • Nerv | 比React小,比Preact大(nervjs@1.3.3 9.8 kB gzipped,不需要compat; react@16.4.0 + react-dom@16.4.0 31.4 kB gzipped)| Nerv的目标是100%使用相同的API(没有Fiber和Suspense),详见NervJS/nerv#10 | IE8支持

    • Inferno | 比React小,大于Preact和Nerv(inferno@5.4.2 + inferno-compat@5.4.2 11.3 kB gzipped; react@16.4.0 + react-dom@16.4.0 31.4 kB gzipped)| 比React更高的运行时性能,是所有React替代品中性能最高的,提供了手动优化的可能性 部分合成事件| IE8原生不受支持

    谨慎迁移到替代品。 一些替代品没有合成事件或缺少一些React 16功能(Preact issue, Inferno issue, Nerv issue)。 但是,许多项目仍然可以在没有任何代码库更改的情况下进行迁移。 请参阅迁移指南:Preact, Inferno, Nerv

    reactstrap

    Reactstrap是基于Bootstrap 4的React库。

    使用babel-plugin-transform-imports删除未使用的模块

    从Reactstrap导入模块时:

    import { Alert } from 'reactstrap';
    

    其他Reactstrap模块也打包到应用程序中并使其更大。

    使用babel-plugin-transform-imports去除未使用的模块:

    // .babelrc
    {
      "plugins": [
        ["transform-imports", {
          "reactstrap": {
            "transform": "reactstrap/lib/${member}",
            "preventFullImport": true
          }
        }]
      ]
    }
    

    要了解它是如何工作的,请查看babel-plugin-transform-imports部分。

    react-bootstrap

    react-bootstrap是基于React的Bootstrap 3库。

    使用babel-plugin-transform-imports删除未使用的模块

    react-bootstrap导入模块时:

    import { Alert } from 'react-bootstrap';
    

    其他react-bootstrap模块也会打包到应用程序中并使其更大。

    使用babel-plugin-transform-imports去除未使用的模块:

    // .babelrc
    {
      "plugins": [
        ["transform-imports", {
          "react-bootstrap": {
            "transform": "react-bootstrap/es/${member}",
            "preventFullImport": true
          }
        }]
      ]
    }
    

    要了解它是如何工作的,请查看babel-plugin-transform-imports部分

    react-router

    React Router是React的流行路由器解决方案。

    使用babel-plugin-transform-imports删除未使用的模块

    从React Router导入模块时:

    import { withRouter } from 'react-router';
    

    其他React Router模块也会打包到应用程序中并使其更大。

    使用babel-plugin-transform-imports去除未使用的模块:

    // .babelrc
    {
      "plugins": [
        ["transform-imports", {
          "react-router": {
            "transform": "react-router/${member}",
            "preventFullImport": true
          }
        }]
      ]
    }
    

    (这是使用React Router v4测试的。)

    要了解它是如何工作的,请查看babel-plugin-transform-imports部分。

    styled-components

    styled-components是一个CSS-in-JS库。

    使用babel-plugin-styled-components压缩代码

    babel-plugin-styled-components插件可以压缩用styled-components编写的CSS代码。请参阅相关文档

    whatwg-fetch

    whatwg-fetch是一个完整的window.fetch() polyfill。

    替换为unfetch

    unfetchwindow.fetch()的500字节polyfill。与whatwg-fetch不同,它不支持完整的window.fetch() API,而是专注于polyfill最常用的部分。

    谨慎迁移到unfetch 虽然它支持最流行的API部分,但如果它依赖于不太常见的东西,您的应用可能会无法正常运行。

    适用于多个库的解决方案

    当然,也有其他库的优化技巧。你可以将它们与常识一起使用,以获得更小或更高性能的bundle包。

    babel-plugin-transform-imports

    这个方便的babel插件会将您的导入转换为仅导入特定组件,这可确保不会包含整个库。

    // Before
    import { Grid, Row, Col } from 'react-bootstrap';
    // After
    import Grid from 'react-bootstrap/lib/Grid';
    import Row from 'react-bootstrap/lib/Row';
    import Col from 'react-bootstrap/lib/Col';
    

    相关文章

      网友评论

          本文标题:使用Webpack优化你的第三方库

          本文链接:https://www.haomeiwen.com/subject/ecvdrctx.html