feat: expose web observe wrapper contract (#894)

Co-authored-by: Codex <codex@noreply.local>
This commit is contained in:
Lyon
2026-06-25 21:45:24 +08:00
committed by GitHub
parent 07fda94925
commit fd874ceef5
5 changed files with 300 additions and 0 deletions
+12
View File
@@ -1,4 +1,5 @@
// SPEC: PJ2026-01060505 Workbench Performance draft-2026-06-17-p0.
// SPEC: PJ2026-01060508 Web哨兵 draft-2026-06-25-p0-web-probe-sentinel.
// Responsibility: YAML-first node/lane operations, including Workbench observability control commands.
import { createHash, randomBytes } from "node:crypto";
import { existsSync, mkdirSync, readFileSync, renameSync, writeFileSync } from "node:fs";
@@ -14,6 +15,8 @@ import { nodeWebObserveAnalyzerSource } from "./hwlab-node-web-observe-analyzer-
import { nodeWebObserveRunnerSource } from "./hwlab-node-web-observe-runner-source";
import { nodeWebObserveCollectViewNodeScript, parseNodeWebProbeObserveCollectView, type NodeWebProbeObserveCollectView } from "./hwlab-node-web-observe-collect";
import { withWebObserveCollectRendered, withWebObserveCommandRendered, withWebObserveStatusRendered } from "./hwlab-node-web-observe-render";
import { buildWebObserveWrapperForObserveOptions, webObserveWrapperStateDirFromStatus } from "./hwlab-node-web-observe-wrapper";
import { renderWebObserveWrapperContract } from "./hwlab-node-web-observe-wrapper-render";
import { hwlabNodeHelp, hwlabNodeObservabilityHelp, hwlabNodeWebProbeHelp } from "./hwlab-node-help";
import { compactWebProbeResult, compactWebProbeScriptResult } from "./hwlab-node-web-probe-summary";
import { nodeObservabilityRecordingRuleExpression, nodeObservabilityRecordingRuleSummaries, nodeObservabilityWarningAlertExpression, nodeObservabilityWarningAlertSummaries } from "./hwlab-node-observability-promql";
@@ -8189,6 +8192,7 @@ function runNodeWebProbeObserveStart(
id: observerId,
credential,
observer: withWebObserveShortcuts(started, observerId),
wrapper: buildWebObserveWrapperForObserveOptions("start", options, spec.workspace, { id: observerId, jobId: observerId, stateDir }),
index,
next: webObserveNextCommands(observerId),
result: compactCommandResultRedacted(result, [material.password ?? ""]),
@@ -8223,6 +8227,7 @@ function runNodeWebProbeObserveStatus(options: NodeWebProbeObserveOptions, spec:
workspace: spec.workspace,
degradedReason,
observer: withWebObserveShortcuts(status, observerId),
wrapper: buildWebObserveWrapperForObserveOptions("status", options, spec.workspace, { id: observerId, stateDir: webObserveWrapperStateDirFromStatus(status, options.stateDir) }),
index,
next: observerId === null ? null : webObserveNextCommands(observerId),
result: compactCommandResultWithStdoutTail(result),
@@ -8323,6 +8328,7 @@ function runNodeWebProbeObserveCommand(options: NodeWebProbeObserveOptions, spec
commandId,
observerCommand: commandSummaryForOutput(payload),
observer: commandResult,
wrapper: buildWebObserveWrapperForObserveOptions(stopCommand ? "stop" : "command", options, spec.workspace, { commandType: type }),
result: compactCommandResult(result),
full: options.full,
valuesRedacted: true,
@@ -8356,6 +8362,7 @@ function runNodeWebProbeObserveForceStop(
commandId,
observerCommand: commandSummaryForOutput(payload),
observer: forcePayload,
wrapper: buildWebObserveWrapperForObserveOptions("stop", options, spec.workspace, { commandType: "stop" }),
forceReason: reason,
preflightObserver: preflightStatus,
preflightResult: preflightResult === null ? null : compactCommandResult(preflightResult),
@@ -8397,6 +8404,7 @@ function runNodeWebProbeObserveCollect(options: NodeWebProbeObserveOptions, spec
requestedGrep: options.collectGrep,
degradedReason: collect === null ? "collect-json-parse-failed" : null,
collect,
wrapper: buildWebObserveWrapperForObserveOptions("collect", options, spec.workspace),
result: collect === null ? compactCommandResultWithStdoutTail(result) : compactCommandResult(result),
valuesRedacted: true,
});
@@ -8834,6 +8842,7 @@ function runNodeWebProbeObserveAnalyze(options: NodeWebProbeObserveOptions, spec
analysis: failureAnalysis,
failure: analysisFailure,
alertThresholds,
wrapper: buildWebObserveWrapperForObserveOptions("analyze", options, spec.workspace),
result: analysis === null ? compactCommandResultWithStdoutTail(result) : compactCommandResult(result),
valuesRedacted: true,
});
@@ -9957,6 +9966,7 @@ function renderWebObserveStartResult(result: Record<string, unknown>): Record<st
]],
),
"",
...renderWebObserveWrapperContract(result),
webObserveTable(
["URL", "TARGET_PATH", "STATE_DIR"],
[[result.url, result.targetPath, webObserveShort(webObserveText(stateDir), 96)]],
@@ -10101,6 +10111,8 @@ function renderWebObserveAnalyzeResult(result: Record<string, unknown>): Record<
["OBSERVER", "NODE", "LANE", "STATUS", "REPORT_JSON", "REPORT_MD"],
[[id, result.node, result.lane, result.status, analysis.reportJsonSha256, analysis.reportMdSha256]],
),
"",
...renderWebObserveWrapperContract(result),
...(blockerRows.length > 0
? ["", webObserveTable(["ANALYZE_BLOCKER", "VALUE"], blockerRows)]
: []),