组件库技术选型总结

Monorepo & Multirepo 架构

Multirepo指的是将模块分为多个仓库,每个团队都拥有自己的仓库,他们可以使用自己的构建流程、代码规范等,但是同时也会存在很多问题,比如模块中间如果存在相互依赖,就必须到目标仓库里进行bug修复、构建、发版本等,相互依赖关系越复杂,处理起来就越困难。

Monorepo指的是将多个模块放在一个仓库中,因此他们可以共享同一套构建流程,代码规范也可以做到统一,特别是如果存在模块间的相互依赖的情况,查看代码、修改bug、调试等会更加方便,因此也越来越受到大家的关注,像 BabelReactVue 等主流的开源仓库都采用的 monorepo

Monorepo Multi-repo
优点 依赖、配置复用方便子项目间依赖 足够简单
缺点 整体项目庞大CI 复杂需要配置,有学习成本 项目间依赖麻烦
适用场景 工具集 项目

技术选择

选择Vue3+Vite

原因:

  1. 选择你最熟悉的技术。考虑到团队如果熟悉该项技术,那么在开发过程中可以很好的控制风险,方便对程序进行优化。
  2. 选择拥有强大生态和社区支撑的开源技术。有强大的生态和社区意味着,很多东西你不需要重复去造轮子,或者遇到问题可以很快解决,有更多的选择。从公司层面、使用活跃的技术也比较好招人。在Vue框架下,基于调研发现elementui的生态比较完善
  3. 选择成长期的技术。我们选择的技术应该是向前发展的、面向未来的, 这是选型的基本原则。从社区活跃度、开发活跃度、issue等都可以看出elementui还是不错的。
  4. **API的稳定性 ** 现在开源项目在API变更上面是非常谨慎的,这点上React和Vue打平

技术路线

最近对前端构建工具的一些理解

包管理工具 - pnpm + workspace

pnpm 提出了 workspace 的概念,内置了对 monorepo 的支持,它与 Lerna + Yarn Workspaces 的配置几乎一样,那么为什么要用 pnpm + pnpm-workspace 取代之前的 lerna + yarn Workspaces 呢?

这里我总结了以下几点原因:

  • lerna 已经不再维护,后续有任何问题社区无法及时响应
  • pnpm装包效率更高,并且可以节约更多磁盘空间
  • pnpm本身就预置了对monorepo的支持,不需要再额外第三方包的支持
  • pnpm CLI 很好用(它是内置的)
  • 它解决了许多 Lerna CLI 存在的问题,像过滤、安装同一个包的多个版本

(几乎)pnpm 所有的命令都支持 --filter 标识符。我认为这个标识符的意思是不言自明的,(但还是要说一下),它表示只会为过滤后的仓库执行这条命令。

假设你有两个完整的应用,两者都有独立的流水线。使用 Lerna + npm 或者 Yarn,当我们执行安装时,我们会为每个项目都单独安装一次依赖。

这意味着,在某些情况下,我们会下载 1GB 的依赖文件而非 300MB。

有了 pnpm,我可以简单地运行下面的指令:

pnpm install --filter website

现在,只有根目录依赖和我的网站的依赖会被安装。filter 命令已经足够便捷了,但是它的好处不止于此,并且还提供了更多的灵活性。

构建工具 - GULP + Webpack

谈到构建工具,大家首先想到的肯定是Webpack和Vite。Webpack功能强大,生态丰富;Vite 采用 unbundle 构建模式,带来了极致的开发体验,给开发人员以新的选择。此外,还有其他的构建工具,如和 WebpackVite 类似的 RollupParcelEsbuild,自动化构建工具 gruntgulp,以及更加久远的 YUI Tool

Grunt / Gulp

Grunt / Gulp 都是运行在 node 环境上的自动化工具。主要用来设定程序自动处理静态资源的工作。

  • 搭建web服务器
  • 文件保存时自动重载浏览器
  • 使用预处理器如Sass、LESS
  • 解析html
  • 代码检查
  • es6 代码转换为 es5
  • 优化资源,比如压缩CSS、JavaScript、压缩图片

不同:

  • 使用 Grunt的过程中,会产生一些中间态的临时文件。一些任务生成临时文件,其他任务可能会基于临时文件再做处理并生成最终的构建稳健,导致出现多次I/O
  • Gulp 有文件流的概念,通过管道将多个任务和操作连接起来,不会产生临时文件,减少了I/O操作,流程更清晰,大大加快了构建速度。

Webpack / Rollup / Parcel

WEBPACK是当下最热门的前端资源模块化管理和打包工具。它可以将许多松散的模块按照依赖和规则打包成符合生产环境部署的前端资源。还可以将按需加载的模块进行代码分隔,等到实际需要的时候再异步加载。通过 loader 的转换,任何形式的资源都可以视作模块。

WebpackRollupParcel 统称为静态模块打包器

这一类构建工具,通常需要指定入口 - entry,然后以 entry 为起点,通过分析整个项目内各个源文件之间的依赖关系,构建一个模块依赖图 - module graph,然后再将 module graph 分离为三种类型的 bundle: entry 所在的 initial bundlelazy load 需要的 async bundle 和自定义分离规则的 custome bundle

这几个构建工具各有优势:

  • Webpack 大而全,配置灵活,生态丰富,是构建工具的首选。
  • Parcel 号称零配置,使用简单,适合不太需要定制化构建的项目使用。
  • Rollup 推崇 ESM 标准开发,打包出来的代码干净,适用于组件库开发。

Webpack 缺点:

  1. 可读性太低 2. 文件很大。阅读Webpack学习时,一些不需要读的额外的bundle代码(子模块定义、子模块引用等等)导致文件体积膨胀,因为1)源码每个独立文件外面都包了一层模块定义 2)模块内对其它模块的引用都插了一条__webpack_require__声明 3)__webpack_require__工具函数自身的体积。 文件体积不仅会带来传输负担,还会影响Compile时间,打包方案的bundle size是一项重要指标 3. 由上一条的分析也可看出这会造成执行很慢的问题

rollup:

优点:1. 文件很小 2. 执行很快 3. es和iife格式支持。支持打包es6模块,对于基础库之类的东西很合适,因为es6项目一般会用babel转一遍,这样保证一次统一的babel翻译。

缺点:1. 插件生态相对较弱,一些常见需求无法满足。比如打包多个依赖库,把公共依赖项提出来(webpack的CommonsChunkPlugin) 2. 早些版本(0.43)循环依赖处理得不好,会出现打包/执行出错 3. 文档相对较少,遇到问题无法快速解决

总结:

相比webpack,rollup拥有无可比拟的性能优势,这是由依赖处理方式决定的,编译时依赖处理(rollup)自然比运行时依赖处理(webpack)性能更好。就应用场景而言,rollup最适合打包成单文件,因为目前rollup对multi entry不很友好(公共依赖项都提不出来)。另外,稳定性及插件生态、文档等还不如webpack,但苛求性能的场景,rollup是唯一的选择。所以,webpack更适合打包组件库、应用程序之类的应用,而rollup更适合打包纯js的类库

Webpack1
   |
   |
Rollup 出现(推崇 ESM 规范,可以实现 tree shaking, 打包出来的代码更干净)
   |
   |
Webpack2(也实现了 tree shaking, 但是配置还是太繁琐了)
   |
   |
Parcel (号称 0 配置)
   |
   |
Webpack4(通过 mode 确定 development 和 production 模式,各个模式有自己的默认配置)
   |
   |
Webpack5(持久化缓存、module federation)

Esbuild(采用 go 语言开发,比 Webpack 更快)

Vite(推崇 ESM 规范,开发模式采用 nobundle,更好的开发体验;生产模式下则基于 rollup 进行构建)

代码管理 - GIT

GIT是一款免费、开源的分布式版本控制系统,用于敏捷高效地处理任何或小或大的项目。它采用了分布式版本库的方式,不必服务器端软件支持,使源代码的发布和交流极其方便。

前端开发库 - VUEJS

VueJS是开源的一个前端开发库,通过简洁API提供高效的数据绑定和灵活的组件系统。

模块加载器 - RequireJS

RequireJS 是一个JavaScript模块加载器。它非常适合在浏览器中使用,但它也可以用在其他脚本环境, 就像 Rhino and Node. 使用RequireJS加载模块化脚本将提高代码的加载速度和质量。

CSS预处理器 - SASS

SASS是一种CSS预处理器。它是对CSS的语法的一种扩充,它可以使用巢状、混入、选择子继承等功能,可以更有效有弹性的写出Stylesheet。Sass最后还是会编译出合法的CSS让浏览可以使用,也就是说它本身的语法并不太容易让浏览器识别(虽然它和CSS的语法非常的像,几乎一样),因为它不是标准的CSS格式,在它的语法内部可以使用动态变量等,所以它更像一种极简单的动态语言。

  • 很多开发者不选用less是因为less输出修改过的css到浏览器需要依赖于javascript引擎,而javascript引擎需要额外的时间来处理。

git钩子husky

https://blog.csdn.net/xiangshj/article/details/114670738

版本控制工具

处理浏览器兼容

1. polyfill

1)为什么要用babel-polyfill

Babel默认只转换新的JavaScript句法(syntax),而不转换新的API,比如 Iterator、Generator、Set、Maps、Proxy、Reflect、Symbol、Promise等全局对象,以及一些定义在全局对象上的方法(比如Object.assign)都不会转码。举个例子,ES6在Array对象上新增了Array.from方法。Babel就不会转码这个方法。如果想让这个方法运行,必须使用babel-polyfill,为当前环境提供一个垫片。

2)安装

npm install babel-polyfill -S

3)在 Node / Browserify / Webpack 中使用

你需要在你的应用入口顶部通过 require 将 polyfill 引入进来。确保它在任何其他代码/依赖声明之前被调用!

require("babel-polyfill");

如果你在你的应用入口使用 ES6 的 import 语法,你需要在入口顶部通过 import 将 polyfill 引入,以确保它能够最先加载:

import 'babel-polyfill';

在 webpack.config.js 中,将 babel-polyfill 加到你的 entry 数组中:

module.exports = {
  entry: ["babel-polyfill", "./app/js"]
};

4)在浏览器中使用

可以在 babel-polyfill npm 发布版中的 dist/polyfill.js 文件中找到它。 它需要在你编译过的 Babel 代码之前被包括进去。你可以将它追加到你编译过的代码中,或者在这些代码之前通过

编码规范

Javascript层

Lint工具

  • ESLint - 目前是社区最流行的、通用的Javascript Lint工具,Lint界的Babel。支持定制插件、preset。如果不想折腾可以选择它的一些预定义配置
  • TSLint - Typescript Lint工具。不过即将废弃了, 推荐使用ESLint

类型检查. 暂时将它们归类到这里,因为它们同属于‘静态测试’

  • Typescript - Javascript语言的超集,这是一门‘新’的语言,而不是简单的类型检查器. 不过它也支持原生Javascript的类型检查
  • Flow - Facebook出品的类型检查器,语法和Typescript类似. 个人推荐使用Typescript

代码格式化

  • Prettier - 关于代码格式化的所有东西都交给它吧!

基本上,所有代码格式相关的工作都可以交给Prettier来做,在这个基础上再使用Eslint覆盖语义相关的检查

按需引入

通过babel插件的方式,将引入组件库和组件样式的模式自动化,antd、antd-mobile、material-ui都在使用的babel-plugin-import、还有ElementUI使用的 babel-plugin-component。在业务项目中配置好babel插件之后,它内部就可以给你做一个这样的转换

代码规范检查

配置 eslint 对代码进行统一的规范校验,配合 lint-staged 可以对已经提交的代码进行校验。lint-staged 是 Git 里的概念,表示暂存区,lint-staged 表示只检查暂存区中的文件。

单元测试

单元测试指标:

一般使用测试覆盖率来量化,尽管对于覆盖率能不能衡量单元测试的有效性存在较多争议。

大部分情况下还是推荐尽可能提高覆盖率, 比如要求语句覆盖率达到70%;核心模块的语句覆盖率和分支覆盖率都要达到100%. 视团队情况而定

相关工具

  • 单元测试

    • AVA
    • Jasmine
    • Mocha
    • Tape
  • 测试框架

    • Jest

      Facebook的单元测试框架. 零配置, 支持组件快照测试、模块Mock、Spy. 一般场景, 单元测试学它一个就行了

      • 组件测试
        • testing-library
        • Enzyme
    • Intern

  • 断言库

    • Chai
    • expect.js
    • should.js
  • Mock/Stubs/Spies

    • sinon.js

文档生成和部署

vuepress是一个文档生成工具,默认的样式和vue官方文档几乎是一致的,因为创造它的初衷就是想为vue和相关的子项目提供文档支持。它内置了 Markdown的扩展,写文档的时候就是用 markdown来写,最让人省心的是你可以直接在 Markdown 文件中使用Vue组件,意味着我们的组件库中写的一个个组件,可以直接放到文档里去用,展示组件的实际运行效果。

对于大多数人来说,可能没有精力去维护一个静态服务器。因此,我们可以选用github pagesgitee pages帮我们托管静态资源,并且是免费的。

发包

遵循semver 语义化版本规范, 也就是1(主版本号).0(次版本号).0(修订版本号)这样的模式。

你可能感兴趣的:(vue.js,前端,javascript,组件库,组件库搭建)