fix: clarify code queue activity counts
This commit is contained in:
committed by
Codex
parent
f3b5b449a2
commit
031c3fda39
@@ -16,6 +16,10 @@ function asArray(value: unknown): unknown[] {
|
||||
return value as unknown[];
|
||||
}
|
||||
|
||||
function manyIds(prefix: string, count: number): string[] {
|
||||
return Array.from({ length: count }, (_, index) => `${prefix}-${String(index + 1).padStart(2, "0")}`);
|
||||
}
|
||||
|
||||
function fixtureResponse(): JsonRecord {
|
||||
return {
|
||||
ok: true,
|
||||
@@ -76,6 +80,66 @@ function fixtureResponse(): JsonRecord {
|
||||
};
|
||||
}
|
||||
|
||||
function splitBrainLiveResponse(): JsonRecord {
|
||||
const liveTaskIds = manyIds("task-running", 8);
|
||||
return {
|
||||
ok: true,
|
||||
status: 200,
|
||||
body: {
|
||||
ok: true,
|
||||
queue: {
|
||||
total: 8,
|
||||
queueCount: 2,
|
||||
activeQueueIds: [],
|
||||
activeTaskIds: [],
|
||||
queuedTaskIds: [],
|
||||
counts: { running: 8 },
|
||||
unreadTerminal: 0,
|
||||
executionDiagnostics: {
|
||||
state: "split-brain",
|
||||
splitBrain: true,
|
||||
splitBrainLive: true,
|
||||
effectiveLiveness: "live",
|
||||
recommendedAction: "continue-supervision",
|
||||
databaseActiveTaskCount: 8,
|
||||
databaseActiveTaskIds: liveTaskIds,
|
||||
schedulerActiveRunSlotCount: 0,
|
||||
schedulerActiveTaskIds: [],
|
||||
activeHeartbeatCount: 8,
|
||||
activeHeartbeatTaskIds: liveTaskIds,
|
||||
heartbeatFreshTaskIds: liveTaskIds,
|
||||
heartbeatExpiredTaskIds: [],
|
||||
heartbeatMissingTaskIds: [],
|
||||
staleRecoveryCandidateTaskIds: [],
|
||||
heartbeatRiskTaskIds: [],
|
||||
},
|
||||
},
|
||||
queues: [
|
||||
{
|
||||
id: "alpha",
|
||||
name: "Alpha",
|
||||
total: 4,
|
||||
counts: { running: 4 },
|
||||
unreadTerminal: 0,
|
||||
activeTaskId: null,
|
||||
runnableTaskId: null,
|
||||
updatedAt: "2026-05-20T00:00:00.000Z",
|
||||
},
|
||||
{
|
||||
id: "beta",
|
||||
name: "Beta",
|
||||
total: 4,
|
||||
counts: { running: 4 },
|
||||
unreadTerminal: 0,
|
||||
activeTaskId: null,
|
||||
runnableTaskId: null,
|
||||
updatedAt: "2026-05-20T00:01:00.000Z",
|
||||
},
|
||||
],
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
function assertQueuesShape(label: string, result: unknown, expectedView: string): void {
|
||||
const data = asRecord(result);
|
||||
const queues = asRecord(data.queues);
|
||||
@@ -100,15 +164,51 @@ function assertQueuesShape(label: string, result: unknown, expectedView: string)
|
||||
assertCondition(liveness.schedulerActiveRunSlotCount === 0, `${label} liveness summary should keep master active slot zero visible`, liveness);
|
||||
assertCondition(asArray(liveness.heartbeatFreshTaskIds).length === 1, `${label} liveness summary should include bounded fresh heartbeat task ids`, liveness);
|
||||
assertCondition(String(liveness.interpretation ?? "").includes("heartbeat is fresh"), `${label} liveness interpretation should explain slot-zero split-brain`, liveness);
|
||||
const activity = asRecord(queues.activity);
|
||||
assertCondition(activity.effectiveActiveTaskCount === 1, `${label} activity should foreground effective active task count`, activity);
|
||||
assertCondition(activity.databaseRunningTaskCount === 1, `${label} activity should distinguish database running tasks`, activity);
|
||||
assertCondition(activity.heartbeatFreshActiveTaskCount === 1, `${label} activity should distinguish heartbeat-fresh active runners`, activity);
|
||||
assertCondition(activity.schedulerLocalActiveQueueCount === 1, `${label} activity should distinguish scheduler-local active queues`, activity);
|
||||
assertCondition(activity.activeQueueIdsScope === "scheduler-local-active-run-slots", `${label} activity should label activeQueueIds scope`, activity);
|
||||
assertCondition(Array.isArray(queues.activeTaskIds), `${label} activeTaskIds should be present`, queues);
|
||||
assertCondition(Array.isArray(queues.queuedTaskIds), `${label} queuedTaskIds should be present`, queues);
|
||||
}
|
||||
|
||||
function assertSplitBrainLiveActivity(label: string, result: unknown): void {
|
||||
const queues = asRecord(asRecord(result).queues);
|
||||
const totals = asRecord(queues.totals);
|
||||
assertCondition(totals.activeQueueCount === 0, `${label} scheduler-local active queue count should be zero`, totals);
|
||||
assertCondition(totals.schedulerLocalActiveQueueCount === 0, `${label} should preserve zero scheduler-local active queues`, totals);
|
||||
assertCondition(totals.runnableQueueCount === 0, `${label} runnable queue count should be zero`, totals);
|
||||
assertCondition(totals.databaseRunningTaskCount === 8, `${label} should foreground DB running task count`, totals);
|
||||
assertCondition(totals.databaseActiveTaskCount === 8, `${label} should foreground DB active task count`, totals);
|
||||
assertCondition(totals.heartbeatFreshActiveTaskCount === 8, `${label} should foreground heartbeat-effective active runners`, totals);
|
||||
assertCondition(totals.effectiveActiveTaskCount === 8, `${label} should foreground effective active task count`, totals);
|
||||
assertCondition(asArray(queues.activeQueueIds).length === 0, `${label} activeQueueIds should remain the scheduler-local list`, queues);
|
||||
assertCondition(queues.activeQueueIdsScope === "scheduler-local-active-run-slots", `${label} activeQueueIds should be scoped`, queues);
|
||||
assertCondition(String(queues.activeQueueIdsNote ?? "").includes("scheduler-local only"), `${label} activeQueueIds note should explain local-only semantics`, queues);
|
||||
const activity = asRecord(queues.activity);
|
||||
assertCondition(activity.effectiveActiveTaskCount === 8, `${label} activity should expose effective active count`, activity);
|
||||
assertCondition(activity.effectiveActiveSource === "heartbeat-fresh", `${label} activity should choose heartbeat-fresh source`, activity);
|
||||
assertCondition(activity.databaseRunningTaskCount === 8, `${label} activity should expose DB running count`, activity);
|
||||
assertCondition(activity.heartbeatFreshActiveTaskCount === 8, `${label} activity should expose heartbeat-effective active count`, activity);
|
||||
assertCondition(activity.schedulerLocalActiveQueueCount === 0, `${label} activity should expose scheduler-local queue count`, activity);
|
||||
assertCondition(activity.schedulerLocalActiveRunSlotCount === 0, `${label} activity should expose scheduler-local slot count`, activity);
|
||||
assertCondition(activity.runnableQueueCount === 0, `${label} activity should expose runnable queue count`, activity);
|
||||
assertCondition(activity.splitBrainLive === true, `${label} activity should preserve split-brain live`, activity);
|
||||
assertCondition(String(activity.activeQueueIdsNote ?? "").includes("zero local queue ids does not mean zero active runners"), `${label} activity note should prevent zero-active misread`, activity);
|
||||
assertCondition(String(activity.interpretation ?? "").includes("continue supervision"), `${label} activity interpretation should keep supervision action`, activity);
|
||||
}
|
||||
|
||||
export function runCodeQueueQueuesShapeContract(): JsonRecord {
|
||||
const fetcher = (path: string): JsonRecord => {
|
||||
assertCondition(path === "/api/microservices/code-queue/proxy/api/queues", "codex queues should use stable proxy path", { path });
|
||||
return fixtureResponse();
|
||||
};
|
||||
const splitBrainFetcher = (path: string): JsonRecord => {
|
||||
assertCondition(path === "/api/microservices/code-queue/proxy/api/queues", "codex queues should use stable proxy path", { path });
|
||||
return splitBrainLiveResponse();
|
||||
};
|
||||
|
||||
const summary = codexQueuesQueryForTest([], fetcher);
|
||||
assertQueuesShape("summary", summary, "summary");
|
||||
@@ -140,6 +240,11 @@ export function runCodeQueueQueuesShapeContract(): JsonRecord {
|
||||
assertCondition(offsetFullQueues.hasPrevious === true, "offset full should expose previous page", offsetFullQueues);
|
||||
assertCondition(asRecord(asArray(offsetFullQueues.items)[0]).id === "gamma", "offset full should return second page rows", offsetFullQueues);
|
||||
|
||||
const splitSummary = codexQueuesQueryForTest([], splitBrainFetcher);
|
||||
assertSplitBrainLiveActivity("split-brain summary", splitSummary);
|
||||
const splitFull = codexQueuesQueryForTest(["--full"], splitBrainFetcher);
|
||||
assertSplitBrainLiveActivity("split-brain full", splitFull);
|
||||
|
||||
return {
|
||||
ok: true,
|
||||
checks: [
|
||||
@@ -150,6 +255,7 @@ export function runCodeQueueQueuesShapeContract(): JsonRecord {
|
||||
"deprecated full array omitted from default output",
|
||||
"full explicit limit remains bounded and paged",
|
||||
"offset pagination",
|
||||
"split-brain live activity counts distinguish scheduler-local queues, DB running tasks, and heartbeat-fresh runners",
|
||||
],
|
||||
};
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user