likes
comments
collection
share

从0发布一个React组件包

作者站长头像
站长
· 阅读数 8

前言

前端技术也是发展比较快,组件化、模块化已成为主流。

当开发的项目中有一些公共组件可以沉淀的时候,将这些组件抽离出来,开发一个组件库无疑是一个好的选择,最近组内也是沉淀了一些工具函数业务组件。 那么怎么去开发一个组件呢?本文将和你一起从零开发一个 React 组件(大佬请绕路)。

技术选型

技术工具

目前比较主流的打包工具有webpack、rollup。最近比较火热的的 Vite 中打包也是依赖 Rollup;相比webpack,rollup更加轻量,专注打包,令人最激动的就是本身天然支持Tree-shaking,让打包文件更快、体积很小。当然,本文也是基于Rollup打包react组件。

前端框架

框架都是大家日常使用中的框架,本文采用React。

快速开始

step1

新建两个文件夹:

  1. react-conponent开发组件。
  2. test-react-component测试组件 从0发布一个React组件包 进入到react-conponen初始化npm package项目并且取名为react-show-title:
cd react-conponent
npm init -y

首先我们安装React相关的包:

npm i react react-dom -D

然后安装我们的打包工具rollup以及相关的依赖(babel)用来解析React JSX:

npm i rollup @babel/core @babel/preset-env @babel/preset-react @rollup/plugin-babel -D

此时得到package.json如下:

{
  "name": "react-show-title",
  "version": "1.0.0",
  "description": "",
  "main": "index.js",
  "scripts": {
    "test": "echo \"Error: no test specified\" && exit 1"
  },
  "author": "",
  "license": "ISC",
  "devDependencies": {
    "@babel/core": "^7.20.5",
    "@babel/preset-env": "^7.20.2",
    "@babel/preset-react": "^7.18.6",
    "@rollup/plugin-babel": "^6.0.3",
    "react": "^18.2.0",
    "react-dom": "^18.2.0",
    "rollup": "^3.6.0"
  }
}

step2

新建rollup.config.mjs 文件 新建scr->index.jsscr->components->ShowTitle.jsx 新建.npmignorebabel.config.json 此时的目录结构就很简单:

├── package.json 
├── src 
    └── components
│       ├── ShowTitle.jsx // 组件源代码
│   └── index.js // 入口文件
├── .babel.config.json
├── .npmignore //  如果不上传到github,.npmignore就可以了,优先级:.npmignore>.gitignore
└── rollup.config.mjs

setp3

  1. 写入配置文件相关信息rollup.config.mjs 写入之前需要安装两个rollup依赖包:
npm i @rollup/plugin-node-resolve @rollup/plugin-commonjs -D

解释:rollup是不会打包外部模块的,@rollup/plugin-node-resolve插件可以让 Rollup 查找到外部模块。@rollup/plugin-commonjs的作用为了解决一些引入的cjs模块(比如:moment,lodash),因为大多数的 NPM 包暴露的都是 CommonJS 模块。

// rollup.config.mjs

import resolve from '@rollup/plugin-node-resolve';
import babel from '@rollup/plugin-babel';
import commonjs from '@rollup/plugin-commonjs';

export default {
  input: 'src/index.js',
  output: [
    {
      file: 'lib/bundle.js',
      format: 'es'
    },
  ],
  plugins: [ resolve(), commonjs(), babel()],
  external: ['react'] // react为外部引入,所系不需要打包进去
}

入口文件src/index.js,打包路径lib/bundle.jses生成指定的bundle格式,关于打包文件的格式解释如下:

  • amd - 异步模块定义,适用于 RequireJS 等模块加载器
  • cjs - CommonJS,适用于 Node 环境和其他打包工具(别名:commonjs
  • es - 将 bundle 保留为 ES 模块文件,适用于其他打包工具以及支持 <script type=module> 标签的浏览器(别名: esmmodule
  • iife - 自执行函数,适用于 <script> 标签。(如果你要为你的应用创建 bundle,那么你很可能用它。)
  • umd - 通用模块定义,生成的包同时支持 amdcjs 和 iife 三种格式
  • system - SystemJS 模块加载器的原生格式(别名: systemjs)。

step4

写入babel配置文件:babel.config.json

// babel.config.json

{
   "presets": [
       "@babel/preset-env",
       "@babel/preset-react"
   ]
}

step5

scr->components->ShowTitle.jsx文件写入:

import React from 'react';
import moment from 'moment';

export default () => {  
    console.log(moment,'moment');
    return <>
        <h1>ShowTitle</h1>
        <span>北京时间:{moment().format('YYYY-MM-DD HH:mm:ss')}</span>
    </>
}

step6

在入口文件把组件抛出去scr->index.js

export { default as ShowTitle } from './components/ShowTitle.jsx'

打包

1、先配置命令package.json:

"scripts": {
    "dev": "npx rollup -wc rollup.config.mjs",
    "build": "npx rollup -c rollup.config.mjs",
  },

2、执行

npm run build

可以看到执行结果lib/bundle.js

从0发布一个React组件包 此时是把外部引入的moment也打包进去了。如果moment不用打包。可以在rollup.config.mjs修改如下:

import resolve from '@rollup/plugin-node-resolve';
import babel from '@rollup/plugin-babel';
import commonjs from '@rollup/plugin-commonjs';

export default {
  ...,
  external: ['react','moment']
}

在执行npm run build

从0发布一个React组件包 此时已经打包成功了。

测试打包组件

1.现在组件已经打包完成了,如果直接发布的话出现bug怎么办?所以在发布之前是需要进行测试的,此时就需要用到npm link

link 的本质就是软链接,这样可以让我们快速使用本地正在开发的其它包。

假设组件库仓库为项目 A,使用组件库的仓库为项目 B。

在项目 A 下运行 npm link,在项目 B 下运行 npm link A,就可以实时调试项目 A 了。 现在我们已经在有了A项目react-conponent。直接在当前我们组件的项目中运行: npm link

注意: 在link之前需要在package.jsonmain字段指定为打包过后的文件路径:

  ...,
  "main": "lib/bundle.js",

2.在test-react-component文件夹起一个react项目,可以用create-react-app快速创建: 此处笔者用webpack简单搭建了React项目

从0发布一个React组件包ReactTest->index.js中写入:

import React from 'react';
import { ShowTitle } from 'react-show-title'

export default () => {
  return (
    <>
    <ShowTitle></ShowTitle>
    </>
  );
}

link到我们开发的组件:

npm link react-show-title

效果:

从0发布一个React组件包

注意link接名字是我们开发的组件名字react-show-title,也就是package.jsonmain对应的值:

{
  "name": "react-show-title",
  "version": "1.0.0",
  "description": "",
  "main": "lib/bundle.js",
  ...
}

组件测试完过后需要unlink:npm unlink react-show-title

发布

1. 注册 npm

如已注册可跳过该步骤。

注册地址:www.npmjs.com/

2. 登录 npm

进入项目根目录,并登录:

npm login

然后你会得到一个让你输入usernamepasswordemail 的提示,把它们填在相应的位置。

关于 package.json 需要注意的点

package.json 里面的配置信息非常重要,我解释一下几个重要的配置。

  • name: 包名。
  • version: 包的版本,每次发布包的版本不能和上次一样。详细规范可见这里
  • description:包的简介。
  • repository:适合写 Github 地址。
  • icense认证。
  • main包的入口文件。引入包的时候去加载的入口文件。
  • keywords:添加关键词,方便npm搜索到。

这个时候我们就可以发布到 npm 了:

npm publish

如果你是私有包,可以这样发布:

npm publish --access=public

小结

这是自己通过rollup如何实现从零的发布react组件,项目是比较简单的实践。真实项目cli远比这复杂。感兴趣的朋友可以自己敲代码实现一下,如果项目中有任何错误,欢迎指正。

最后: 项目中如果真的需要沉淀项目组件,在写组件之前先check有没有现成的组件可以直接复用,把不必要的时间节省出来创造其他价值。