Rollup小记

1 个月前

前言

     最近在做一个react.js的组件库,并发布成npm包,在这个过程中选择了Rollup来做代码打包,细节东西还挺多,那就笔记一下,省的忘记不知道到哪里找。用了Rollup真心觉得很小巧,很容易上手。现在流行的一些javascript库都是通过Rollup进行打包的,看来这个工具作用不小哈!

Rollup

  • 一个 JavaScript 模块打包器
  • 使用Tree Shaking,自动移除未使用的代码, 输出更小的文件
  • 可以一次输出多种格式:(IIFE, AMD, CJS, UMD, ESM)
    IIFE:一个立即执行函数表达式,JavaScript 引擎到此将直接执行函数 CJS:CommonJS是nodejs也就是服务器端广泛使用的模块化机制
    UMD:通用模块定义,以amd,cjs 和 iife 为一体 ESM: ES Modules 是用于处理模块的 ECMAScript 标准,这个标准化过程在 ES6 中完成,浏览器开始实施这个标准
    AMD: 异步模块

Rollup.config.js

核心就在这个配置文件,根据官方给出的设置按自己需要加,这里配置output文件类型的时候,有格的格式必须添加name参数

const config = {
  input: 'src/index.js', //输入
  output: [ //输出
    {
      file: pkg.module,
      format: 'umd', //大部分在浏览器端会使用umd
      name:'' //根据输出类型配置
    },
  ],
  external: [ //外部依赖的包
    'react',
    'react-dom',
  ],
  plugins: [], //插件配置
};

插件库

想要完成多种前端体系打包,Rollup提供了丰富的插件库,让开发者不在担心,接下来把使用到的一一道来。

  1. rollup-plugin-babel
    这个是最要的,在项目会写入es6/7等版本javascript代码,需要转译才能在浏览器上兼容性更好

    import { rollup } from 'rollup';
    import babel from 'rollup-plugin-babel';
    
    rollup({
      plugins: [
        babel({
          exclude: 'node_modules/**'
        })
      ]
    })
    
  2. rollup-watch
    实时监听代码更改,当代码发生变化时,会自动编译文件更新内容,安装插件后只要在配置文件执行命令上加 "-w"即可

      {
       // ...
       "scripts": {
         "build": "rollup -c",
         "dev": "rollup -c -w"
       }
     }
    

    Rollup本身也提供了watch的API,当它检测到磁盘上单个模块已经改变,它会重新构建你的文件束,看下官方实例,而我现在没有这样使用。

     const rollup = require('rollup');
    
     const watchOptions = {...};
     const watcher = rollup.watch(watchOptions);
    
     watcher.on('event', event => {
       // event.code 会是下面其中一个:
       //   START        — 监听器正在启动(重启)
       //   BUNDLE_START — 构建单个文件束
       //   BUNDLE_END   — 完成文件束构建
       //   END          — 完成所有文件束构建
       //   ERROR        — 构建时遇到错误
       //   FATAL        — 遇到无可修复的错误
     });
    
     // 停止监听
     watcher.close();
    
  3. rollup-plugin-postcss和autoprefixer
    在我的开发过程中用sass写css样式,需要这2个插件来配合。

     import postcss from 'rollup-plugin-postcss';
     import autoprefixer from 'autoprefixer';
     const config = {
         plugins: [
           postcss({ extract: true, plugins: [autoprefixer] })
         ]
     };
    

    如果使用postcss,就需要多加几个包

     import postcss from 'rollup-plugin-postcss';
    
      // 新增 postcss plugins
     import simplevars from 'postcss-simple-vars';
     import nested from 'postcss-nested';
     import cssnext from 'postcss-cssnext';
     import cssnano from 'cssnano';
    
     const config = {
         plugins: [
           postcss({
             extensions: ['.css'],
             plugins: [
               simplevars(),
               nested(),
               cssnext({ warnForDuplicates: false, }),
               cssnano()
             ]
          })
         ]
     };
    
  4. rollup-plugin-commonjs
    目前 npm 上大多数模块使用了 CommonJS 风格,在此之前,需要将 CommonJS 转换为 ES2015才能使用

     import commonjs from 'rollup-plugin-commonjs';
    
     const config = {
         plugins: [
           commonjs({ 
               sourceMap: false,  // 非CommonJS模块将被忽略 
               ignoreGlobal: false //如果为true,则此插件不会处理“global”的使用
               ...
           })
         ]
     };
    
  5. rollup-plugin-peer-deps-external
    当使用汇总绑定库时,我们通常希望避免包含对等依赖项,因为它们应该由库的使用者提供。通过排除这些依赖项,我们可以减小捆绑大小,避免捆绑重复的依赖项。
    我们可以使用Rollup外部配置选项来实现这一点,为它提供一个要从包中排除的对等依赖项列表。此插件自动执行该过程,自动将库的对等依赖项添加到外部配置中。

     import peerDepsExternal from 'rollup-plugin-peer-deps-external';
    
     const config = {
         plugins: [
            peerDepsExternal()
         ]
     };
    
  6. rollup-plugin-filesize
    在打包完成时候现实出打包文件的体积大小,这个帮助我们分析包体积,并调整控制

     import filesize from 'rollup-plugin-filesize';
    
     const config = {
         plugins: [
            filesize()
         ]
     };
    

    屏幕快照 2019-07-12 上午11.52.58.2fda14ca8a95.png

  7. rollup-plugin-eslint
    代码检查,需要创建 .eslintrc 文件配置 eslint 规则

     import eslint from 'rollup-plugin-eslint';
    
     const config = {
         plugins: [
             eslint({
                 include: ['src/**/*.js'] // 需要检查的部分
             }),
         ]
     };
    
  8. rollup-plugin-node-resolve
    查找外部模块并安装

     import localResolve from 'rollup-plugin-local-resolve';
    
     const config = {
         plugins: [
             localResolve()
         ]
     };
    
  9. rollup-plugin-uglify
    代码压缩,我们打包必备功能

     //这样使用,会提示uglify is not a function
     import uglify from 'rollup-plugin-uglify'; 
    
     //正确使用
     import { uglify } from 'rollup-plugin-uglify'; 
    
     const config = {
         plugins: [
             uglify()
         ]
     };
    
  10. rollup-plugin-node-resolve
    使用Node解析算法定位模块,以便在node_modules中使用第三方模块

    import nodeResolve from 'rollup-plugin-node-resolve';
    
    const config = {
        plugins: [
            nodeResolve()
        ]
    };
    
  11. rollup-plugin-replace
    类似Webpack的DefinePlugin,通过process.env.NODE_ENV区分本地环境(Development)还是线上环境(Production)

    import replace from 'rollup-plugin-replace';
    
    const config = {
        plugins: [
            replace({
              ENVIRONMENT: JSON.stringify('production')
            })
        ]
    };
    
  12. rollup-plugin-typescript
    如果使用ts,就用这个插件

    import typescript from 'rollup-plugin-typescript';
    
    const config = {
        input: './main.ts',
        plugins: [
            replace({
                typescript({lib: ["es5", "es6", "dom"], target: "es5"})
            })
        ]  
    };
    
  13. rollup-plugin-livereload 和 rollup-plugin-serve
    实时刷新页面功能

    import serve from 'rollup-plugin-serve';
    import livereload from 'rollup-plugin-livereload';
    
    const config = {
        plugins: [
              serve({
                open: true, // 是否打开浏览器
                contentBase: './', // 入口html的文件位置
                historyApiFallback: true,
                host: 'localhost',
                port: 3000
              }),
              livereload()
        ]  
    };
    
  14. rollup-plugin-multi-entry
    有时候我们需要多个入口打包集成的方案,这个插件很好的解决此问题
    1.全局控制

    import multiEntry from "rollup-plugin-multi-entry";
    
    const config = {
        input: '../file.js',
        plugins: [
              multiEntry()
        ]  
    };
    

    2.指定匹配文件

    import multiEntry from "rollup-plugin-multi-entry";
    
    const config = {
        input: './glob/files/**/*.js',
        plugins: [
              multiEntry()
        ]  
    };
    

    3.如果想配置多个,如下

    import multiEntry from "rollup-plugin-multi-entry";
    
    const config = {
        input: ['user/user.js', 'file/files.js', '/globs/**/*.js'],
        plugins: [
              multiEntry()
        ]  
    };
    

结尾

Rollup可以将多文件打包成单文件,而且打包后的文件阅读很清晰,而webpack打包后的代码看上去“不太美观”,Rollup还有很多插件,比如:

  • rollup-plugin-license 增加文件头部注释
  • rolup-plugin-multidest 多出口打包
    ... 等等
    使用过程中是给我蛮舒服的体验,以后开发s类的用Rollup还是很不错的选择
0
推荐阅读