美文网首页
Rollup - 开发UI库入门

Rollup - 开发UI库入门

作者: Lisa_Guo | 来源:发表于2019-12-06 16:22 被阅读0次

本文示例如何基于RollupVue编写一个HelloWorld的UI库

一、初始化项目

生成package.json

mkdir base-ui
cd base-ui
npm init

安装npm包

npm install --save-dev rollup rollup-plugin-vue vue vue-template-compiler 
npm install --save-dev rollup-plugin-babel @babel/core
npm install --save-dev rollup-plugin-node-resolve rollup-plugin-commonjs 
npm install --save-dev rollup-plugin-terser rollup-plugin-css-only clean-css

二、配置文件

增加rollup配置文件 rollup.config.js,支持umd es iiffe格式(分别用于node、es6、browser)

import commonjs from 'rollup-plugin-commonjs'
import resolve from 'rollup-plugin-node-resolve'
import babel from 'rollup-plugin-babel'
import vue from 'rollup-plugin-vue'
import { terser } from 'rollup-plugin-terser'
import css from 'rollup-plugin-css-only' // 提取css
import CleanCSS from 'clean-css'   // 压缩css
import { writeFileSync } from 'fs' // 写文件

module.exports = {
  input: 'src/index.js', // 入口
  output: [
{
    file: 'dist/base-ui.umd.js', // 打包文件名
    name: 'base-ui',
    format: 'umd', // 打包模块支持方案,可选 amd, cjs, es, iife, umd
  }, {
    file: 'dist/base-ui.es.js',
    format: 'es'
  }, {
    name: 'base-ui',
    file: 'dist/base-ui.min.js',
    format: 'iife'
  }],
  plugins: [
    // css({output: 'dist/base-ui.css'}),
    css({ output(style) {
      // 压缩 css 写入 dist/base-ui.css
      writeFileSync('dist/base-ui.css', new CleanCSS().minify(style).styles)
    } }),
    vue({
      // css: false 将<style>块转换为导入语句,rollup-plugin-css-only可以提取.vue文件中的样式
      css: false,
      normalizer : '~rollup-plugin-vue/runtime/normalize',
      // styleInjector : '~rollup-plugin-vue/runtime/browser',
    }),                    
    // terser(),
    resolve(),
    babel({
      exclude: ['node_modules/**']
    }),
    commonjs()
  ],
  external: [ // 不被打包的库
    'vue'
  ]
}

插件说明

  1. rollup-plugin-vue:负责处理vue文件,相当于webpackvue-loader。可选参数见这里

5.0以后的rollup-plugin-vue需要明确指定normalizer : '~rollup-plugin-vue/runtime/normalize',,否则打包输出文件有__vue_normalize__相关的引用错误。

2 rollup-plugin-commonjs
该插件负责将Commonjs模块转化成ES6以便rollup打包。很多npm包都是commonjs模块,需要结合此插件一起使用

  1. rollup-plugin-node-resolve
    rollup只能加载相对路径模块(即通过/,./, ../引入的模块),而三方模块(node_modules里模块)有两种方式打包:
    • rollup.config.js配置为external资源: 输出bundle中不包含此模块,作为external外部资源引入,由使用该bundle组件库的客户程序安装
// rollup.config.js
export default {
  entry: 'src/index.js',
  dest: 'bundle.js',
  format: 'cjs',
  external: [ 'vue' ] // <-- suppresses the warning
};

此时,需要在组件库的package.json中增加外部依赖

"dependencies": {
    "vue": "^2.5.0"
  }

客户端程序安装该组件库时会自动安装dependencies定义的模块

  • rollup-plugin-node-resolve:该插件可以将三方模块包含在输出bundle中。具体见官网介绍
  1. rollup-plugin-babel: 在rollup项目中使用babel,详细见这里

  2. rollup-plugin-terser: 压缩输出后js

  3. rollup-plugin-css-only: 提取css为独立文件

  4. clean-css:压缩css

package.json最终代码为:

{
 "name": "base-ui",
 "version": "1.0.0",
 "description": "A demo for how to create a UI library with Rollup",
 "main": "index.js",
 "scripts": {
   "build": "rollup -c",
   "test": "echo \"Error: no test specified\" && exit 1"
 },
 "author": "",
 "license": "ISC",
 "devDependencies": {
  "@babel/core": "^7.7.4",
   "clean-css": "^4.2.1",
   "node-sass": "^4.13.0",
   "rollup": "^1.27.8",
   "rollup-plugin-babel": "^4.3.3",
   "rollup-plugin-commonjs": "^10.1.0",
   "rollup-plugin-css-only": "^1.0.0",
   "rollup-plugin-node-resolve": "^5.2.0",
   "rollup-plugin-terser": "^5.1.2",
   "rollup-plugin-vue": "^5.1.2",
   "vue-template-compiler": "^2.6.10"
 }
}

三、开发组件库

3.1 开发组件

src/button/index.vue 编写UI组件

<template>
  <h1>Button</h1>
</template>

<script>
export default {
  name: 'my-buttom',
  created() {
    console.log('hello world')
  }
}
</script>

3.2 打包全部组件

src/index.js 输出组件。其中install函数可使组件库当做Vue插件使用,全局注入组件库。请参考VUE插件

import Button from './button/Index.vue'

const components = [Button];
// 全局注入组件
const install = function(Vue) {
  if (!Vue || install.installed) return
  components.forEach(component => {
     Vue.component(component.name, component);
  })
}

 if (typeof window != 'undefined' && window.Vue) {
    install(window.Vue)
  }

export {
  Button
}

export default {
  install
};
npm run build

输出文件dist/base-ui.umd.js如下

(function (global, factory) {
  typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory() :
  typeof define === 'function' && define.amd ? define(factory) :
  (global = global || self, global['base-ui'] = factory());
}(this, (function () { 'use strict';

  var script = {
    name: 'my-button',
    created() {
      console.log('hello world');
    }

  };

  ...

  var index = {
    install
  };

export default index;
export {  __vue_component__ as Button};
})));

3.3 输出单独组件

输出单独组件以支持按需加载
rollup.component.config.js增加用于输出组件的配置文件

import commonjs from 'rollup-plugin-commonjs'
import resolve from 'rollup-plugin-node-resolve'
import babel from 'rollup-plugin-babel'
import vue from 'rollup-plugin-vue'
import { terser } from 'rollup-plugin-terser'
import css from 'rollup-plugin-css-only' // 提取css
import CleanCSS from 'clean-css'   // 压缩css
import { writeFileSync } from 'fs' // 写文件

module.exports = {
  input: 'src/Button/index.js', // 入口
  output: {
    file: 'dist/button/index.js',
    format: 'es'
  },
  plugins: [
    css({ output(style) {
      // 压缩 css 写入 dist/base-ui.css
      writeFileSync('dist/button/index.css', new CleanCSS().minify(style).styles)
    } }),
    vue({
      // css: false 将<style>块转换为导入语句,rollup-plugin-css-only可以提取.vue文件中的样式
      css: false,
      normalizer : '~rollup-plugin-vue/runtime/normalize',
      // styleInjector : '~rollup-plugin-vue/runtime/browser',
    }),                    
    // terser(),
    resolve(),
    babel({
      exclude: ['node_modules/**']
    }),
    commonjs()
  ]
}

执行命令rollup -c rollup.component.config.js输出组件

(function (global, factory) {
  typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory() :
  typeof define === 'function' && define.amd ? define(factory) :
  (global = global || self, global['base-ui'] = factory());
}(this, (function () { 'use strict';

  var script = {
    name: 'my-button',
    created() {
      console.log('hello world');
    }

  };

  ...

export {  __vue_component__ as Button};
})));

四、测试组件库

4.1 创建测试项目

vue create examples 创建项目,用于模拟实际项目引入组件库

全局引入
examples/src/main.js中引入组件,全局注入组件

import MyComponent from '../../dist/base-ui.es'
import MyComponent from '../../dist/base-ui.css'
Vue.use(MyComponent)

examples/src/components/HelloWorld.vue中使用组件

<template>
  <div id="app">
    <my-index></my-index>
  </div>
</template>

按需引入
src/components/HelloWorld.vue中引入Button

...
import { Button } from '../../../dist/button/index.es'

export default {
  components: {
    [Button.name]: Button
  },
}
...

bable-plugin-import
bable-plugin-import可以帮助用户方便地实现按需加载
bable.config.js配置文件中增加配置(如下为mand-mobile配置):

{
  "plugins": [
    ["import", {
      "libraryName": "mand-mobile",  // 组件库名称
      "libraryDirectory": "lib"  // 组件所在目录
    }]
  ]
}

import { Button } from 'mand-mobile'
babel-plugin-import会将以上引入语句转换为下面写法
import Button from 'mand-mobile/lib/button'

4.2 测试

组件项目package,json下增加执行命令, 启动组件库和示例项目的开发模式

"scripts": {
    "dev": "rollup -c --watch",
    "example": "cd examples && npm run serve",
    ...
}

组件项目 package.json里增加入口文件

...
"main": "dist/base-ui.umd.js",
"module": "dist/base-ui.es.js",
"unpkg": "dist/base-ui.min.js",
...

Issues

examples项目里从组件输出目录(/dist)引入组件时默认会启动eslint,编译会报语法错误。暂时取消lint


源码:https://github.com/guolixincl/examples/tree/master/rollup/base-ui


参考文章

  1. https://jsprogram.cn/blog/rollup-config-for-vue-ui-library/
  2. https://www.jianshu.com/p/0c42ae0f1f2b

相关文章

  • Rollup - 开发UI库入门

    本文示例如何基于Rollup和Vue编写一个HelloWorld的UI库 一、初始化项目 生成package.js...

  • rollup开发自己的组件库(1)

    开发的时候有这种需求,我们需要自己做自己公司的js/ui组件库,这时我们用rollup来进行组件库的开发至于放在那...

  • 2018-06-17

    基于rollup的组件库打包体积优化 背景 前段时间对公司内部的组件库(类似element-ui)做了打包体积优化...

  • rollup用法

    10分钟快速入门rollup.js 10分钟快速进阶rollup.js

  • iOS开发-UI 从入门到精通(二)

    iOS开发-UI 从入门到精通(二)是对 iOS开发-UI 从入门到精通(一)知识点的巩固,主要以习题练习为主,增...

  • iOS开发-UI 从入门到精通(三)

    iOS开发-UI 从入门到精通(三)是对 iOS开发-UI 从入门到精通(一)知识点的综合练习,搭建一个简单地登陆...

  • vue-cli3携手rollup、github-actions打

    前言 旨在让开发者在开发时拥有 享受组件开发 一个长得还不错的demo rollup类库打包工具对代码的抚摸 es...

  • 开发Vue UI库教程

    做前端开发的朋友多少都有使用过一些UI库的经验,下面是如何参照element-ui开发一款属于自己的ui库 MS-...

  • 给移动开发者的声明式 UI 入门手册

    前言 我会用两篇文章来讲透声明式 UI,分别是《给移动开发者的声明式 UI 入门手册》,《UI 开发的革命,声明式...

  • React-UI教程

    使用开源的ant-design库开发项目指南 1. 最流行的开源React UI组件库 material-ui(国...

网友评论

      本文标题:Rollup - 开发UI库入门

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