名词解释
- 多个项目的代码放在在同一存储库中这种开发策略称之为
Monorepo
lerna
Babel开发用来管理多包的工具,基于Monorepo
理念在工具端的实现yarn
Facebook 贡献的 Javascript 包管理器commitlint
用来规范git commit信息
背景
在 vue-json-schema-form 项目中,需要把 lib
、doc
、demo
放在同一个项目中管理,彼此独立,又可以相互依赖。
使用 yarn workspace
可以很好的解决上面的问题,搭配 lerna
做npm发布管理。目前大型仓库都使用这种方式,比如 Vue
Vuepress
等。
由于 yarn workspace
和 lerna
有较多的功能重叠,这里重叠的部分优先使用 workspace
。最后就是只有发布管理使用了 learn
其它使用 workspace
详细的可参考 https://github.com/lljj-x/vue... 配置。
创建项目
目录结构
├── packages
| ├── lib
| | ├── package.json
| ├── demo
| | ├── package.json
├── package.json
packages
下每个文件夹为一个单独完整的包
package.json配置
{
"private": true, // 禁止发布
"repository": "https://github.com/lljj-x/vue-json-schema-form",
"workspaces": [
"packages/lib",
"packages/demo",
// "packages/*" // 可以单个指定 也可直接配置 *
]
}
子package配置
子package即为每个独立的工作区。
如:packages/demo
,使用 vue-cli
cd packages && vue create demo
demo/package.json
配置:
{
"private": true, // 禁止发布
"publishConfig": {
"access": "publish" // 如果该模块需要发布,对于scope模块,需要设置为publish,否则需要权限验证
}
}
yarn workspace
yarn install
安装所有依赖,包含子package依赖,如果子package之间存在相互依赖会通过创建软链
的方式引用,而非npm下载,这里可能会影响webpack配置中使用 node_modules
做路径判断的地方。
yarn install
依赖树关系
yarn workspaces info
安装/删除依赖模块
单个package工作区
# packageA 安装 axios
yarn workspace packageA add axios
# packageA 移除 axios
yarn workspace packageA remove axios
packageA
是需要安装依赖的包名,即package.json
中的name
字段,而非目录名
root package
# root package 安装 commitizen
yarn add -W -D commitizen
# root package 移除 commitizen
yarn remove -W commitizen
运行单个 package 的scripts 命令
# 运行packageA 的dev命令
yarn workspace packageA dev
# 这里是在每个工作区运行 run build 命令
yarn workspaces run build
Tips:这里运行命令的时候不会检测依赖树关系,只是package.json
文件workspaces
配置工作区逐个运行,这里推荐使用lerna build
见下文 lerna build
到这里对于不需要推送npm的情况下已经可以满足基本需要了。
lerna
目前使用lerna主要来做发布和版本管理
- 全局安装
npm i -g lerna
- 初始化一个项目
lerna init
包含两种工作模式:
- Fixed/Locked mode (default)
固定模式,默认
packages下的所有包共用一个版本号(version),会自动将所有的包绑定到一个版本号上(该版本号也就是 lerna.json
中的 version
字段),所以任意一个包发生了更新,这个共用的版本号就会发生改变。
- Independent mode
独立模式,允许每一个包有一个独立的版本号,在使用 lerna publish
命令时,可以为每个包单独制定具体的操作,同时可以只更新某一个包的版本号。
lerna.json
中的version
字段指定为independent
即可,或者lerna init --independent
命令初始化
lerna.json
文件配置大致如下
{
"npmClient": "yarn",
"useWorkspaces": true, // 使用yarn workspaces
"version": "0.0.1", // 当前版本 或者 independent 独立模式
"command": {
"version": {
"allowBranch": "master",
"exact": true,
"ignoreChanges": [
"**/*.md"
],
"message": "build: release version %v"
}
}
}
lerna clean
清除所用的 node_modules
目录
lerna clean
lerna diff
显示修改内容 类似git diff
lerna diff
lerna ls
列出所有的子package
lerna ls -l
lerna changed
列出修改过的子package
lerna changed
lerna build
build 所有子package,子package分别执行 build
,--sort
参数可以控制以拓扑排序规则执行命令
lerna run --stream --sort build
lerna version
lerna version
的作用是进行 version bump
,支持手动和自动两种模式
手动确定新版本
# 按着提示选择版本即可
lerna version
自动确定版本
自动根据 conventional commit
规范确定版本
存在feat提交: 需要更新minor版本
存在fix提交: 需要更新patch版本
存在BREAKING CHANGE提交: 需要更新大版本
# 生成changelog文件以及根据commit来进行版本变动
lerna version --conventional-commits
# 生成changelog文件以及根据commit来进行版本变动,不提示用户输入版本
lerna version --conventional-commits --yes
可参见官方文档 lerna version
version
成功后会自动推送当前分支,可以结合配置 lerna.json
文件 command
下 version
字段 配置允许version的分支,commit
信息等
{
"npmClient": "yarn",
"useWorkspaces": true,
"version": "0.0.1",
"command": {
"version": {
"allowBranch": "master",
"exact": true,
"ignoreChanges": [
"**/*.md"
],
"message": "build: release version %v"
}
}
}
lerna publish
lerna publish
的功能可以即包含version的工作,也可以单纯的只做发布操作。
可参见官方文档 lerna publish
lerna publish
lerna publish
会先调用 lerna version,再确定是否要发布到npm
lerna publish from-git
from-git
基于当前git提交的软件包做发布,一般都是通过 lerna version
提交的版本
lerna publish from-package
from-package
在注册表中不存在该版本的最新提交中发布程序包 (这个我没用过)
lerna
不会发布标记为私有的软件包(package.json
中"private": true
)
changelog
根据 conventional commit
提交规范,即可通过工具为每个 package
生成 changelog
文件。
conventional commit 支持
conventional commit规范使用也可以看这个:Commit message 和 Change log 编写指南
安装如下依赖:
yarn add -W -D commitizen cz-conventional-changelog @commitlint/cli @commitlint/config-conventional husky conventional-changelog-cli
commitizen:
一个撰写合格 Commit message
的工具
cz-conventional-changelog:
用于使 commitizen
支持Angular的Commit message格式
配置 package.json
添加如下配置
{
"config": {
"commitizen": {
"path": "./node_modules/cz-conventional-changelog"
}
}
}
至此就可以通过 git cz
命令替换 git commit
生成符合格式的Commit message。
git cz
命令出现如下选项
@commitlint/cli:
commitlint 用于检查您的提交消息是否符合提交格式,类似 eslint
校验js语法
@commitlint/config-conventional:
commitlint 校验规则,类似 eslint-config-standard
添加并配置 .commitlintrc.js
文件
module.exports = {
extends: ['@commitlint/config-conventional'],
rules: {
...otherRules // 可以继续配置你的规则
}
};
husky:husky
是 Git hooks 工具,这里用于在 commit
时校验message内容
配置 package.json
文件,添加如下
{
"husky": {
"hooks": {
"commit-msg": "commitlint -E HUSKY_GIT_PARAMS"
}
}
}
至此当新提交的commit message 不符合规范便会阻止提交。
conventional-changelog-cli:
根据commit message生成 changelog.md
文件 (这里功能和 lerna version --conventional-commits
生成changelog 有部分重叠,下文会详细区分)。
如:conventional-changelog -p angular -i CHANGELOG.md -s -r 2
注意:这里生成的是整个仓库的changelog
,而非每个 package生成changelog
生成changelog
生成changelog 依赖如上 conventional-commit
规范message
整个仓库 changelog
生成自从上次发布以来的变动:
conventional-changelog -p angular -i CHANGELOG.md -w
如果这是您第一次使用此工具,并且想要生成所有以前的变更日志,则可以执行:
conventional-changelog -p angular -i CHANGELOG.md -s -r 0
每个package工作区独立 changelog
lerna version 时,自动模式 --conventional-commits
命令会同时为每个package工作区生成 changelog
lerna version --conventional-commits
注: lerna version
成功之后便会为每个 package 生成 changelog,包括 root package
npm scripts
如下:自己常配的一些script
{
"scripts": {
"demo:dev": "yarn workspace demo dev",
"demo:build": "yarn workspace demo build",
"changelog": "conventional-changelog -p angular -i CHANGELOG.md -s -r 2",
"clean": "lerna clean && rm -rf node_modules",
"packages:diff": "lerna diff",
"packages:list": "lerna ls -l",
"packages:changed": "lerna changed",
"packages:build": "lerna run --stream --sort build",
"publish": "lerna publish",
"autoPublish": "lerna publish --conventional-commits --yes",
"version": "lerna version --conventional-commits --yes"
}
}
changelog
生成整个仓库changelog
publish
手动选择版本并发包 (其实我自己平时一般用这个)autoPublish
自动确定版本并发包同时生成每个package changelogversion
自动确定版本不发布和生成每个package changelog
参考:https://zhuanlan.zhihu.com/p/...
原文发布在:https://www.lljj.me/
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。