美文网首页
rollup打包js库

rollup打包js库

作者: 37手游技术部 | 来源:发表于2021-02-23 18:09 被阅读0次

    前言

    最近在写一个前端工具库,刚开始用webpack搭建,但是偶然间发现rollup的介绍,发现rollop更满足我的需求。这篇文章介绍了用rollup搭建一个简单版的js工具库。

    需求

    代码层面
    1.编写:支持ES6语法(支持异步) 对传参有要求
    2.提交:提交代码有规范
    3.测试:代码测试-单元测试
    4.注释:生成相应的文档说明
    功能层面:
    1.使用:主流浏览器使用;eg:chrome,firefox
    2.js方法
    3.引用:会引用了其它的库
    显然,在打包时,我们第一时间会想到的就是webpack,但是我在实际中发现有更适合我的需求的打包框架,就是rollup。下面我们来看看他们的区别。
    webpack VS Rollup
    1.入口文件
    webpack和rollup都需要一个配置文件,来指定入口,输出,插件等

    webpack rollup
    相对路径 不支持,使用path.resolve 支持

    这只是其中一个简单的区别,我们再来看看以下几个区别
    2.死代码消除(tree-shaking)
    当我们打开一个网页,如图,只有页面加载完相关资源(eg:js,图片)页面才会显示出来。如果我们需要加载的资源体积越小,当然我们打开页面的时间就会缩短。如何缩小我们需要资源的大小呢,tree-shaking就是其中一种方法,通过它减少在项目里没有使用的代码,来减少我们打开页面的时间。

    tree.png

    我们再来看看对于相同的代码webpack和rollup打包的结果

    相同的代码 webpack rollup
    执行时间 71ms 17ms
    文件大小 389KB 262KB

    主要原因就是rollup使用了tree-shaking,利用了es6模块特性,促使了mudle进行静态分析,在uglify阶段删除了无用代码。
    至于什么是es6规范呢,如下:

    • 只能作为模块顶层的语句出现(import和export语句只能出现在代码顶层)
    • import的模块只能是字符串变量,不能使用字符串和变量
    • 引入模块不能再进行修改
    // 情况1 
    let str = '只能作为模块顶层的语句出现';
    import {  sum} from 'util' ;
    
    // 情况2
    import { 's'+'um'} from 'util';
    
    //情况3
    import {sum} from 'util'
    sum=1;// Syntax Error : 'a' is read-only;
    

    3.实时加载
    webpack:使用webpack-dev-server插件
    rollup:rollup-plugin-serve+rollup-plugin-livereload 。
    webpack实时加载的定制型更强,比如添加中间件,指定运行使用的文件。
    更多的比较可去查看。
    总结一下:
    webpack
    生态圈丰富 (文档更完整,插件库丰富)
    拆分代码,按需加载 利用插件支持tree-shaking(webpack 2以上)
    webpack会产生很多额外的代码,
    打包文件较大 执行较慢 可读性弱
    适用涉及到css html 静态资源处理 复杂的代码拆分合并或者 应用
    rollup
    插件生态相对较弱 把所有资源放在同一个地方,一次性加载 利用tree-shaking缩小包体积
    一般不会产生额外的代码,执行更快,可读性更强
    rollup多适用于基础库
    我们再来梳理一下我们的需求:
    1.只需要实现js常用方法 --rollup
    2.语法:支持类型 --TypeScript
    3.规范:编码规范 --ESLint&Prettier
    4.提交:提交有要求 --Husky&commitlint
    5.质量:测试用例 --jest
    下面开始我们的项目搭建啦
    初始化项目
    a.创建文件夹 rollup-demo
    b.npm init -y 初始化
    c.安装 rollup和每次打包清除dist目录插件 npm i rollup rollup-plugin-clear -D
    d.创建入口文件src/main.js

    
    function fun1(){
      
      function fun2(){
        return 'no'
      }
     return 'yes'
    }
    fun1()
    console.log(fun1())
    function Useless(){
      console.log(1111)
    }
    

    e.在根目录下创建rollup.config.js

    'use strict';
    import clear from 'rollup-plugin-clear';
    export default {
      input: 'src/main.ts',
      output: {
        file: 'dist/bundle.js',
        format: 'umd', //打包文件格式
      },
      plugins: [
        clear({targets: ['dist']}), //清除dist目录
      ],
    };
    

    f.在package下添加命令

     "build": "rollup -c rollup.config.js",
    

    执行npm run build
    一个简单的rollup打包项目完成了。
    使用ts
    为什么使用ts呢,ts是静态类型,js是动态类型;静态类型对阅读代码是友好的;同时IDE提供的大量便捷支持和TS本身的语法检查和代码提示自动补全让开发者提高效率,方便重构等。当然,TypeScript 只是为 JavaScript 中本身就存在的使用方式提供了对应的类型标注,所有在 TypeScript 中能够使用的开发模式,在 JavaScript 中一定是本身就存在的。
    a. 安装依赖库
    typescript:编译 typescript 语法的基础库
    rollup-plugin-typescript2:结合 rollup 编译 typescript 的 plugins

    npm i rollup-plugin-typescript2 typescript -D
    

    b. rollup.config.js配置

    rollup.config.js
    import ts from "rollup-plugin-typescript2";
    export default {
        input: "./src/main.ts",
        plugins: [
            ts({
                useTsconfigDeclarationDir: true
            }),
        ]
    }
    

    useTsconfigDeclarationDir:指定生成声明文件存放目录。
    c.配置 tsconfig.json

    {
      "compilerOptions": {
        "target": "es5",// 编译目标
        "module":"es2015",// 模块类型
        "lib": ["es2015", "es2016", "es2017"],// 导入库类型定义
        "strict": true,// 严格模式
        "sourceMap": true,// 生成定义sourceMap
          "strictNullChecks": true, // 不允许把null、undefined赋值给其他类型的变量
        "declaration": true,// 生成定义文件
        "declarationDir": "dist/types",//类型声明文件位置 自动创建声明文件(.d.ts)
        "noUnusedLocals": true, // 未使用变量报错
        "outDir": "./dist",  // 编译输出目录 
        "typeRoots": [ //typeRoots 用来指定默认的类型声明文件查找路径,默认为 node_modules/@types
          "node_modules/@types"
        ]
      }
    }
    

    ** ESLint & Prettier**
    ESLint 对应的是代码语法质量规则,Prettier 对应的是格式化规则。**
    ESLint 是一个插件化的 javascript 代码检测工具,它可以用于检查常见的 JavaScript 代码错误,也可以进行代码风格检查,这样我们就可以根据自己的喜好指定一套 ESLint 配置,然后应用到所编写的项目上,从而实现辅助编码规范的执行,有效控制项目代码的质量。
    prettier 是代码格式化工具。它通过解析代码并使用自己的规则重新打印它,并考虑最大行长来强制执行一致的样式,并在必要时包装代码。支持 JavaScriptFlowTypeScriptCSSSCSSLessJSXVueGraphQLJSONMarkdown 等语言,可以结合 ESLint 和 Prettier,检测代码中潜在问题的同时,还能统一团队代码风格,从而促使写出高质量代码,来提升工作效率。
    a.安装依赖

    • eslint:eslint 核心库,负责整个 eslint 的调度工作
    • @typescript-eslint/parser:ESLint的解析器,用于解析typescript,从而检查和规范Typescript代码
    • @typescript-eslint/eslint-plugin:ESLint插件,包含了各类定义好的检测 typescript 代码的规范
    • prettier:prettier 核心库
    • eslint-config-prettier:解决 ESLint 中的样式规范和 prettier 中样式规范的冲突,以 prettier 的样式规范为准,使 ESLint 中的样式规范自动失效
    • eslint-plugin-prettier:将 prettier 的规范作为 ESLint 规范来使用
    npm i eslint @typescript-eslint/parser @typescript-eslint/eslint-plugin prettier eslint-config-prettier eslint-plugin-prettier -D
    

    b.创建 .eslintrc.js

    module.exports = {
        root: true,
        parser: '@typescript-eslint/parser',
        parserOptions: {
            ecmaVersion: 2019,
            sourceType: 'module', 
       },
           extends: [
            'plugin:@typescript-eslint/recommended',
            'prettier/@typescript-eslint',
            'plugin:prettier/recommended',
        ],
        env: {
            es6: true,
            node: true,
        },
      
        rules: {
            "no-undef": "error",
            "eqeqeq": "error",
              "no-console": "error"
        },
    };
    
    

    c.创建.prettierrc.js

    
    module.exports = {
        arrowParens: 'avoid',
        bracketSpacing: false,
        endOfLine: 'lf',
        jsxBracketSameLine: false,
        jsxSingleQuote: false,
        printWidth: 100,
        proseWrap: 'preserve',
        semi: true,
        singleQuote: true,
        // tabWidth: 4,
        useTabs: false,
        trailingComma: 'es5',
     
    };
    
    

    提交代码规范 Husky & lint-staged & Commitlint
    **Husky **是一个 git hook 辅助工具,能够在 git 文件状态变更时,执行一些操作。husky能够防止不规范代码被commit、push、merge等等
    **lint-staged **能监测到所有提交变动的文件,对其执行一系列命令,如 prettier 对不符合规范的代码进行 fix。
    **commitlint **顾名思义就是进行提交代码 git commit -m 'xxxxx' 时,检查提交记录 message 的,commitlint 能够抵挡住不符合规范的 message 记录,如 git commit -m 'add eslint' 这就是一个不符合规范的 commit ,因为他没有加上对应的 commit type 类别,add eslint 对应的类别应该是 chore (构建过程或辅助工具的变动)
    **a.安装依赖 **

    • husky:git hook 辅助工具
    • lint-staged:监测变动文件并执行命令
    • @commitlint/cli:commitlint 核心工具库
    • @commitlint/config-conventional:一些 commitlint 规则预设
    npm i husky lint-staged -D
    npm i @commitlint/cli @commitlint/config-conventional -D
    
    

    b.创建huskyrc.js

    module.exports = {
      hooks: {
        'commit-msg': 'commitlint -e $HUSKY_GIT_PARAMS',
        'pre-commit': 'lint-staged',// 在 pre-commit commit 前的阶段,执行 lint-staged 中的命令。
      },
    };
    
    

    c.创建 lint-staged.config.js

    module.exports = {
      '{src,test}/**/*.ts': [
        'npm run lint',
        'git add'
      ]
    };
    
    

    d.创建commitlint.config.js

    module.exports = {
      extends: [
        "@commitlint/config-conventional"
      ],
      rules: {// 自定义配置
        'subject-case': [2, 'always', ['upper-case']]
      }
    };
    
    

    **jest测试
    **Jest 是用来创建、执行和构建测试用例的一个 JavaScript 测试 库。可以在任何项目中安装使用它,如 Vue/React/Angular/Node/TypeScript 等。
    简单总结一下,Jest 具有以下优点:

    • 测试用例并行执行,更高效
    • 强大的 Mock 功能
    • 内置的代码覆盖率检查,不需要在引入额外的工具
    • 集成 JSDOM,可以直接进行 DOM 相关的测试
    • 开箱即用,几乎不需要额外配置
    • 可以直接对 ES Module Import 的代码测试
    • 有快照测试功能,可对 React 等框架进行 UI 测试

    a.安装依赖

    • jest:集成测试框架
    • @types/jest: jest 的类型定义包,在 typescript 环境下使用 jest 需要用到
    • ts-jest:测试 typescript 代码的转换工具
    npm i jest @types/jest ts-jest -D
    

    b.创建 jest.config.js

    
    module.exports = {
      // 测试目录
      roots: ['<rootDir>/test'],
      // 对 ts tsx 文件使用 ts-jest 进行运行测试
      transform: {
        '.(ts|tsx)': 'ts-jest',
      },
      // 测试环境
      testEnvironment: 'node',
      // 测试文件匹配
      testRegex: '(/__tests__/.*|\\.(test|spec))\\.(ts|tsx|js)$',
      collectCoverage: true,
      // 不计入覆盖率中
      coveragePathIgnorePatterns: ['/node_modules/', '/test/'],
      // 覆盖率达标阈值,不达标即测试失败,抛出 error
      coverageThreshold: {
        global: {
          branches: 90,
          functions: 95,
          lines: 95,
          statements: 95,
        },
      },
    };
    
    

    c.在根目录下创建 test/main.test.ts

    import Sum from '../src/main'
    test('sum is right', () => {
        expect(Sum(1, 2)).toBe(10);
    });
    
    

    **d.package.json 加上新的 script 指令 "test": "jest" **
    **

    总结

    本篇文章讲解了webpack和rollup的区别,用rollup搭建了一个简单版js库,也使用了TS,ESLint和Prettier 规范代码规范和提交代码的规范和使用jest来保障代码的质量。代码已上传到github。https://github.com/turning1998/baselib

    相关文章

      网友评论

          本文标题:rollup打包js库

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