Commit 2a074e9f by lijiabin

【需求 25171】chore: 测试环境部署分支数量达到上限时,支持在控制台勾选并删除旧分支后继续部署

parent bd21693c
...@@ -3,6 +3,7 @@ import ssh from "ssh2"; ...@@ -3,6 +3,7 @@ import ssh from "ssh2";
import archiver from "archiver"; import archiver from "archiver";
import fs from "node:fs"; import fs from "node:fs";
import path from "node:path"; import path from "node:path";
import inquirer from "inquirer";
import { getCurrentBranchName, getDeploySlug } from "./util.js"; import { getCurrentBranchName, getDeploySlug } from "./util.js";
// 当前分支名 // 当前分支名
...@@ -430,22 +431,81 @@ ${metaContent} ...@@ -430,22 +431,81 @@ ${metaContent}
EOF`); EOF`);
} }
// 已部署分支数量达到上限时,直接在控制台勾选要删除的分支,删完继续部署。
// 返回删除后剩余的分支列表;用户取消 / 不是交互终端 / 删的不够时返回 null,调用方终止部署
async function cleanUpBranches(deployEntries) {
const needRemoveCount = deployEntries.length - MAX_DEPLOY_BRANCH_COUNT + 1;
console.log(`当前已部署分支数量已达到上限 ${MAX_DEPLOY_BRANCH_COUNT},需要先删除至少 ${needRemoveCount} 个:`);
deployEntries.forEach((item, index) => {
console.log(`${index + 1}. ${item.branchName} (${item.slug}) ${item.deployedAt}`);
});
if (!process.stdin.isTTY) {
console.log("当前终端不是交互模式,无法选择,请手动到服务器上删除后重试");
return null;
}
const { slugs } = await inquirer.prompt([
{
type: "checkbox",
name: "slugs",
message: `请选择要删除的分支(空格选中,回车确认,至少选 ${needRemoveCount} 个,不选直接回车则取消部署)`,
choices: deployEntries.map((item) => ({
name: `${item.branchName} (${item.slug}) ${item.deployedAt}`,
value: item.slug,
})),
validate: (value) =>
value.length === 0 || value.length >= needRemoveCount
? true
: `至少要选 ${needRemoveCount} 个才有空位`,
},
]);
if (slugs.length === 0) {
console.log("已取消部署");
return null;
}
const { confirmed } = await inquirer.prompt([
{
type: "confirm",
name: "confirmed",
message: `将从服务器永久删除 ${slugs.length} 个分支的部署目录,删除后无法恢复,确认吗?`,
default: false,
},
]);
if (!confirmed) {
console.log("已取消部署");
return null;
}
for (const slug of slugs) {
// 目录名来自服务器上 find 出来的结果,这里再校验一次再拼进 rm 命令,避免 .. 或带特殊字符的名字
if (!/^[\w-]+$/.test(slug)) {
throw new Error(`目录名不合法,已停止删除:${slug}`);
}
await execCommand(`rm -rf '${remoteRootPath}/${slug}'`);
console.log(`已删除:${slug}`);
}
return deployEntries.filter((item) => !slugs.includes(item.slug));
}
async function start() { async function start() {
try { try {
await connectServer(); await connectServer();
const folderList = await getFolderList(); const folderList = await getFolderList();
const deployEntries = await getDeployEntries(folderList); let deployEntries = await getDeployEntries(folderList);
const alreadyDeployed = deployEntries.some((item) => item.slug === deploySlug); const alreadyDeployed = deployEntries.some((item) => item.slug === deploySlug);
if (!alreadyDeployed && deployEntries.length >= MAX_DEPLOY_BRANCH_COUNT) { if (!alreadyDeployed && deployEntries.length >= MAX_DEPLOY_BRANCH_COUNT) {
console.log( deployEntries = await cleanUpBranches(deployEntries);
`当前已部署分支数量已达到上限 ${MAX_DEPLOY_BRANCH_COUNT},请先手动删除以下分支中的一个或多个:`, if (!deployEntries) {
); return;
deployEntries.forEach((item, index) => { }
console.log(`${index + 1}. ${item.branchName} (${item.slug})`);
});
return;
} }
await writeIndexHtml(deployEntries); await writeIndexHtml(deployEntries);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment