-
Notifications
You must be signed in to change notification settings - Fork 2
/
release.js
75 lines (58 loc) · 2.58 KB
/
release.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
'use strict';
const fs = require('fs');
const childProcess = require('child_process');
const path = require('path');
const semver = require('semver');
const moment = require('moment');
const PACKAGE_JSON_PATH = path.join(process.cwd(), 'package.json');
const CHANGELOG_PATH = path.join(process.cwd(), 'CHANGELOG.md');
const packageFile = require(PACKAGE_JSON_PATH);
function exec (command) {
return childProcess.execSync(command).toString().slice(0, -1);
}
const githubRepoUrl = exec('git config --get remote.origin.url').replace(/\.git$/, '');
function updatePackageJson (version) {
fs.writeFileSync(PACKAGE_JSON_PATH, JSON.stringify(Object.assign({}, packageFile, { version }), null, 2) + '\n');
}
function updateChangelog (newText) {
fs.writeFileSync(CHANGELOG_PATH, newText);
}
function createGitCommit (version) {
exec(`git commit -am 'Build: update package.json and changelog for v${version}'`);
}
function createGitTag (version) {
exec(`git tag v${version}`);
}
function getCommitSubject (commitHash) {
return exec(`git --no-pager show -s --oneline --format=%s ${commitHash}`);
}
function getAbbreviatedCommitHash (commitHash) {
return exec(`git --no-pager show -s --oneline --format=%h ${commitHash}`);
}
function getCommitLink (commitHash) {
return `[${getAbbreviatedCommitHash(commitHash)}](${githubRepoUrl}/commit/${commitHash})`;
}
function replaceIssueLinks (message) {
return message.replace(/#(\d+)/g, `[#$1](${githubRepoUrl}/issues/$1)`);
}
const commitHashes = exec(`git log --format=%H v${packageFile.version}...HEAD`).split('\n').filter(hash => hash);
if (!commitHashes.length) {
throw new RangeError('No commits since last release');
}
const commitSubjects = commitHashes.map(getCommitSubject);
let newVersion;
if (commitSubjects.some(subject => subject.startsWith('Breaking'))) {
newVersion = semver.inc(packageFile.version, 'major');
} else if (commitSubjects.some(subject => subject.startsWith('Update') || subject.startsWith('New'))) {
newVersion = semver.inc(packageFile.version, 'minor');
} else {
newVersion = semver.inc(packageFile.version, 'patch');
}
const newChangelogHeader = `## v${newVersion} (${moment.utc().format('YYYY[-]MM[-]DD')})`;
const commitLines = commitHashes.map(hash => `* ${replaceIssueLinks(getCommitSubject(hash))} (${getCommitLink(hash)})`);
const oldChangelog = fs.readFileSync(CHANGELOG_PATH).toString();
const newChangelog = oldChangelog.replace(/^(# Changelog\n\n)/, `$1${newChangelogHeader}\n\n${commitLines.join('\n')}\n\n`);
updatePackageJson(newVersion);
updateChangelog(newChangelog);
createGitCommit(newVersion);
createGitTag(newVersion);