52 lines
2.4 KiB
TypeScript
52 lines
2.4 KiB
TypeScript
import type { Worker } from "./types";
|
||
import { workerAgeText } from "./client";
|
||
|
||
// CHV 可用性纯逻辑:不发请求、不拼 URL,只从 ctx 已有的
|
||
// /workers 数据推断。非管理员的 /workers 只返回聚合数
|
||
// (workers_total/online/offline),没有按执行器的分项,
|
||
// 此时 CHV 在线数是未知,绝不能把未知写成 0,也绝不能
|
||
// 把聚合在线数当成 CHV 在线数。
|
||
export function isWorkerAlive(w: Worker): boolean {
|
||
if (w.alive !== undefined && w.alive !== null) return !!w.alive;
|
||
const info = workerAgeText(w);
|
||
return info.age !== null && info.age <= 120;
|
||
}
|
||
|
||
export function countChvWorkers(workers: Worker[]): { online: number; total: number } {
|
||
const chv = workers.filter((w) => w.executor === "cloud-hypervisor");
|
||
return { online: chv.filter(isWorkerAlive).length, total: chv.length };
|
||
}
|
||
|
||
export type ChvAvailability =
|
||
| { state: "known"; online: number; total: number }
|
||
| { state: "unknown"; reason: "not-loaded" | "aggregate-only" | "load-failed" };
|
||
|
||
export function chvAvailability(
|
||
workers: Worker[] | null,
|
||
workersSummary: string,
|
||
workersError: string,
|
||
): ChvAvailability {
|
||
if (workers) return { state: "known", ...countChvWorkers(workers) };
|
||
if (workersError) return { state: "unknown", reason: "load-failed" };
|
||
if (workersSummary.includes("无 worker 注册")) return { state: "known", online: 0, total: 0 };
|
||
if (workersSummary.includes("完整 worker 清单仅全局管理员可见")) {
|
||
return { state: "unknown", reason: "aggregate-only" };
|
||
}
|
||
return { state: "unknown", reason: "not-loaded" };
|
||
}
|
||
|
||
// 排队原因提示:只在“已知零 CHV worker 在线 + CHV 任务排队”时
|
||
// 给出,文案明确写“可能原因”,且不编造后端未返回的
|
||
// VM 状态/IP/快照。未知时返回空串(不提示、不猜测)。
|
||
export function chvQueueHint(
|
||
executor: string | undefined | null,
|
||
status: string | undefined | null,
|
||
availability: ChvAvailability,
|
||
): string {
|
||
if (executor !== "cloud-hypervisor" || status !== "queued") return "";
|
||
if (availability.state === "known" && availability.online === 0) {
|
||
return "可能原因:当前无 cloud-hypervisor worker 在线,任务在排队(基于 /workers 推断;VM 状态/IP/快照等后端未返回字段不展示)。请先确认 KVM 宿主上的 CHV worker 已起,worker 上线后可认领。";
|
||
}
|
||
return "";
|
||
}
|