跳到主要内容

自动化发布

如果你的项目遵循语义化版本控制,自动化发布所需的步骤可能是个好主意。 下面的配方会提升项目版本号,将更改提交到git,并创建一个新的GitHub发布版本。

要发布GitHub版本,你需要创建一个个人访问令牌并将其添加到你的项目中。但是,我们不想把它提交到代码库,所以我们将使用dotenv从一个被git忽略的.env文件中加载它:

GH_TOKEN=ff34885...

别忘了将.env添加到.gitignore文件中。

接下来,安装此配方所需的所有依赖项:

npm install --save-dev conventional-recommended-bump conventional-changelog-cli conventional-github-releaser dotenv execa

根据你的环境、设置和偏好,你的发布工作流可能看起来像这样:

const gulp = require('gulp');
const conventionalRecommendedBump = require('conventional-recommended-bump');
const conventionalGithubReleaser = require('conventional-github-releaser');
const execa = require('execa');
const fs = require('fs');
const { promisify } = require('util');
const dotenv = require('dotenv');

// 加载环境变量
const result = dotenv.config();

if (result.error) {
throw result.error;
}

// Conventional Changelog预设
const preset = 'angular';
// 将命令的输出打印到终端
const stdio = 'inherit';

async function bumpVersion() {
// 根据提交获取推荐的版本提升
const { releaseType } = await promisify(conventionalRecommendedBump)({ preset });
// 提升版本但不提交和标记
await execa('npm', ['version', releaseType, '--no-git-tag-version'], {
stdio,
});
}

async function changelog() {
await execa(
'npx',
[
'conventional-changelog',
'--preset',
preset,
'--infile',
'CHANGELOG.md',
'--same-file',
],
{ stdio }
);
}

async function commitTagPush() {
// 尽管在这种情况下我们可以使用"require",但我们采取安全路线
// 因为"require"会缓存值,所以如果我们碰巧在其他地方再次使用"require"
// 我们将不会获取当前值,而是获取上次调用"require"时的值
const { version } = JSON.parse(await promisify(fs.readFile)('package.json'));
const commitMsg = `chore: release ${version}`;
await execa('git', ['add', '.'], { stdio });
await execa('git', ['commit', '--message', commitMsg], { stdio });
await execa('git', ['tag', `v${version}`], { stdio });
await execa('git', ['push', '--follow-tags'], { stdio });
}

function githubRelease(done) {
conventionalGithubReleaser(
{ type: 'oauth', token: process.env.GH_TOKEN },
{ preset },
done
);
}

exports.release = gulp.series(
bumpVersion,
changelog,
commitTagPush,
githubRelease
);