目的
- 为了控制网站版本,老页面可通过判断网站版本来决定是否更新网站(即刷新网页)
- 为了避免开发者在一些重大更新后忘记设置版本号
可行性
既然可以在 pre-commit
阶段校验和格式化代码,那么就可以在 pre-push
阶段调用命令行执行设置版本号相关的命令
具体做法
效果广告是通过 ant-design-pro 搭建的,它自带了
yorkie
,可以类似husky
的githook工具
- 修改
pre-push
(什么是gitHook),在.git => hooks => pre-push
,添加一句exec < /dev/tty
。完整内容为:
#!/bin/sh
#yorkie 2.0.5
command_exists () {
command -v "$1" >/dev/null 2>&1
}
has_hook_script () {
if [ $1 == 'pre-commit' ];then
return 0
fi
[ -f package.json ] && cat package.json | grep -q "\"$1\"[[:space:]]*:"
}
# OS X and Linux only
load_nvm () {
# If nvm is not loaded, load it
command_exists nvm || {
export NVM_DIR="$1"
[ -s "$1/nvm.sh" ] && . "$1/nvm.sh"
}
}
# OS X and Linux only
run_nvm () {
# If nvm has been loaded correctly, use project .nvmrc
command_exists nvm && [ -f .nvmrc ] && nvm use
}
cd "."
# Check if pre-push is defined, skip if not
has_hook_script pre-push || exit 0
# Node standard installation
export PATH="$PATH:/c/Program Files/nodejs"
# Export Git hook params
export GIT_PARAMS="$*"
# allow interactive shell commands
exec < /dev/tty
# Run hook
node "./node_modules/@umijs/yorkie/src/runner.js" pre-push || {
echo
echo "pre-push hook failed (add --no-verify to bypass)"
exit 1
}
- 修改
package.json
文件,添加pre-push
脚本
"gitHooks": {
"pre-push": "node publish.js"
}
- 在项目根目录(或者其他你喜欢的任何地方,相应地,你需要修改步骤2中的脚本路径)。添加
publish.js
脚本
#!/usr/bin/env node
const commander = require('commander');
const inquirer = require('inquirer');
const semver = require('semver');
const chalk = require('chalk');
const shell = require('shelljs');
const program = new commander.Command();
const { version } = require('./package.json');
function isValidNewVersion(oldVersion, newVersion) {
return !!(semver.valid(newVersion) || semver.inc(oldVersion, newVersion));
}
async function inputVersion() {
// 弹出当前版本,并提示用户输入最新版本号
const { newVersion } = await inquirer.prompt([
{
type: 'input',
message: `请输入版本号(当前版本:${version})`,
name: 'newVersion',
},
]);
if (isValidNewVersion(version, newVersion) && semver.lt(version, newVersion)) {
console.log('更新版本中,请稍等...');
try {
// 更改package的version
if (
shell.exec(`npm version ${newVersion} --no-commit-hooks --no-git-tag-version`).code !== 0
) {
console.log(chalk.red('更新失败'));
shell.echo('Error: npm version error');
shell.exit(1);
} else {
new Promise((resolve) => {
const addCode = shell.exec(`git add .`).code;
const commitCode = shell.exec(`git commit -m "v${newVersion}" --no-verify`).code;
if (addCode === 0 && commitCode === 0) {
console.log(chalk.green(`更新版本成功,最新版本:${newVersion}`));
resolve();
} else {
shell.exit(1);
}
});
}
} catch (err) {
console.log(err, chalk.grey('err~!'));
shell.exit(1);
}
} else {
// 提示输入不合法,重新输入
console.error(
chalk.red('输入不合法,请遵循npm语义化'),
chalk.underline('https://semver.org/lang/zh-CN/'),
);
inputVersion();
}
}
async function main() {
if (!shell.which('git')) {
shell.echo('Sorry, this script requires git');
shell.exit(1);
}
// 只有在 master 或 develop 分支才会弹出
const allowBranch = ['master', 'develop'];
const gitBranchName = shell.exec(`git rev-parse --abbrev-ref HEAD`, { silent: true });
if (allowBranch.includes(gitBranchName.stdout.trim())) {
program.version(version).action(async () => {
const { update } = await inquirer.prompt([
{
type: 'confirm',
message: '是否更新网站版本?',
name: 'update',
},
]);
if (update) {
await inputVersion();
}
});
await program.parseAsync(process.argv);
} else {
console.log(chalk.yellow(`当前分支为:${gitBranchName.stdout}不执行版本更新操作`));
}
}
main();
实际效果
git push
的时候即可看到实际效果