fix: compact codex pr preflight output

This commit is contained in:
Codex
2026-05-23 01:06:09 +00:00
parent 6f40350a62
commit d4c6fadc49
5 changed files with 329 additions and 72 deletions
@@ -347,10 +347,11 @@ async function main(): Promise<void> {
assertCondition(asRecord(fallback.disclosure).fullObservationsOmitted === true, "healthy remote fallback should disclose omitted full observations", fallback.disclosure);
assertCondition(asRecord(fallback.localObservationSummary).failureKind === "target-stack-not-running", "healthy remote fallback should keep bounded local observation summary", fallback.localObservationSummary);
assertCondition(asRecord(fallback.remoteObservationSummary).ok === true, "healthy remote fallback should keep bounded remote observation summary", fallback.remoteObservationSummary);
const fallbackPreflight = asRecord(fallback.preflight);
assertCondition(fallbackPreflight.ok === true, "remote fallback preflight should stay ready", fallbackPreflight);
assertCondition(asRecord(fallbackPreflight.tokenCoverage).source === "GH_TOKEN", "token source should be GH_TOKEN", fallbackPreflight.tokenCoverage);
assertCondition(asRecord(fallbackPreflight.prCapabilityContract).targetBranch === "master", "target branch should stay master", fallbackPreflight.prCapabilityContract);
assertCondition(fallback.preflight === undefined, "remote fallback default output should omit detailed preflight", fallback);
const fallbackSchedulerPreflight = asRecord(fallback.schedulerPreflight);
assertCondition(fallbackSchedulerPreflight.authReady === true, "remote fallback scheduler summary should stay ready", fallbackSchedulerPreflight);
assertCondition(fallbackSchedulerPreflight.authSource === "GH_TOKEN", "token source should be GH_TOKEN", fallbackSchedulerPreflight);
assertCondition(asRecord(fallback.prCapability).targetBranch === "master", "target branch should stay master", fallback.prCapability);
const authMissing = await codexPrPreflightQueryForTest(["--remote"], {
config: null,
@@ -406,23 +407,26 @@ async function main(): Promise<void> {
assertCondition(directAuthObservationGap.kind === "runner-local-observation-gap", "auth missing after remote fallback should keep local backend-core absence scoped as runner-local observation gap", directAuthObservationGap);
const directAuthSummary = asRecord(directAuthMissingRecord.authScopeSummary);
const directAuthScopeBoundary = asRecord(directAuthMissingRecord.scopeBoundary);
const directAuthActiveRunner = asRecord(directAuthMissingRecord.activeRunnerDevContainer);
const directAuthActiveRunner = asRecord(directAuthMissingRecord.activeRunnerPrCapability);
const directAuthRecommendedActions = Array.isArray(directAuthMissingRecord.recommendedActions) ? directAuthMissingRecord.recommendedActions : [];
assertCondition(directAuthSummary.schedulerAuthMissingIsScoped === true, "remote auth-missing should lead with scheduler-scoped auth summary", directAuthSummary);
assertCondition(String(directAuthSummary.interpretation ?? "").includes("does not prove"), "remote auth summary must not imply active runner PR incapability", directAuthSummary);
assertCondition(directAuthScopeBoundary.scopesAreIndependent === true, "remote auth-missing must distinguish scheduler env from active runner dev container", directAuthScopeBoundary);
assertCondition(directAuthScopeBoundary.schedulerAuthMissingDoesNotMeanActiveRunnerCannotCreatePr === true, "remote auth-missing should expose the explicit PR capability boundary", directAuthScopeBoundary);
assertCondition(String(directAuthScopeBoundary.authMissingInterpretation ?? "").includes("do not simplify"), "remote auth-missing must warn against overbroad interpretation", directAuthScopeBoundary);
assertCondition(directAuthActiveRunner.notEquivalentToSchedulerEnv === true, "active runner token capability must be a separate scope", directAuthActiveRunner);
assertCondition(directAuthActiveRunner.independentOfSchedulerPreflight === true, "active runner token capability must be a separate scope", directAuthActiveRunner);
assertCondition(Array.isArray(directAuthMissingRecord.recommendedActions), "remote auth-missing should expose bounded recommended actions", directAuthMissingRecord.recommendedActions);
assertCondition(directAuthRecommendedActions.length === 3, "remote auth-missing recommended actions should stay bounded", directAuthRecommendedActions);
assertCondition(directAuthRecommendedActions.some((action) => asRecord(action).action === "verify-current-runner-auth"), "remote auth-missing should recommend active runner auth status first", directAuthRecommendedActions);
assertCondition(directAuthRecommendedActions.some((action) => String(asRecord(action).command ?? "").includes("gh pr create") && asRecord(action).writesRemote === false), "remote auth-missing should recommend PR create dry-run", directAuthRecommendedActions);
assertCondition(directAuthMissingRecord.localObservation === undefined, "auth-missing remote fallback default output should omit full local observation", directAuthMissingRecord);
assertCondition(directAuthMissingRecord.remoteObservation === undefined, "auth-missing remote fallback default output should omit full remote observation", directAuthMissingRecord);
assertCondition(directAuthMissingRecord.preflight === undefined, "auth-missing remote fallback default output should omit detailed preflight", directAuthMissingRecord);
assertCondition(asRecord(directAuthMissingRecord.disclosure).fullObservationsOmitted === true, "auth-missing remote fallback should disclose omitted full observations", directAuthMissingRecord.disclosure);
assertCondition(asRecord(directAuthMissingRecord.disclosure).fullDetailOmitted === true, "auth-missing remote fallback should disclose omitted full detail", directAuthMissingRecord.disclosure);
assertCondition(asRecord(directAuthMissingRecord.localObservationSummary).failureKind === "target-stack-not-running", "auth-missing remote fallback should keep bounded local observation summary", directAuthMissingRecord.localObservationSummary);
assertCondition(asRecord(asRecord(directAuthMissingRecord.remoteObservationSummary).tokenCoverage).scope === "scheduler-runner-env", "auth-missing remote fallback should keep bounded remote token scope", directAuthMissingRecord.remoteObservationSummary);
assertCondition(JSON.stringify(directAuthMissingRecord).length < 12000, "auth-missing remote fallback default output should stay compact", { chars: JSON.stringify(directAuthMissingRecord).length });
const directAuthMissingFull = await codexPrPreflightQueryForTest(["--remote", "--full"], {
config: { network: { publicHost: "74.48.78.17", frontend: { port: 18081 } } } as unknown as UniDeskConfig,
@@ -599,15 +603,63 @@ async function main(): Promise<void> {
assertCondition(githubTransientRecord.runnerDisposition === "infra-blocked", "GitHub transient keeps infra-blocked disposition for legacy callers", githubTransientRecord);
assertCondition(githubTransientRecord.retryable === true, "GitHub transient should expose top-level retryable=true", githubTransientRecord);
assertCondition(githubTransientRecord.commanderAction === "retry-backoff-or-keep-running-if-heartbeat-fresh", "GitHub transient should expose top-level commander action", githubTransientRecord);
const githubTransientPreflight = asRecord(githubTransientRecord.preflight);
assertCondition(githubTransientPreflight.retryable === true, "GitHub transient preflight should be retryable", githubTransientPreflight);
assertCondition(githubTransientPreflight.commanderAction === "retry-backoff-or-keep-running-if-heartbeat-fresh", "GitHub transient should expose bounded commander action", githubTransientPreflight);
const githubTransient = asRecord(githubTransientPreflight.githubTransient);
assertCondition(githubTransientRecord.preflight === undefined, "GitHub transient default output should omit detailed preflight", githubTransientRecord);
const githubTransient = asRecord(githubTransientRecord.githubTransient);
assertCondition(githubTransient.kind === "github-transient", "GitHub transient evidence should identify kind", githubTransient);
assertCondition(githubTransient.notAuthMissing === true, "GitHub transient must not be auth-missing", githubTransient);
assertCondition(githubTransient.notPrSemanticFailure === true, "GitHub transient must not be PR semantic failure", githubTransient);
assertCondition(Array.isArray(githubTransient.failedProbes) && githubTransient.failedProbes.length <= 4, "GitHub transient evidence should stay bounded", githubTransient);
assertCondition(String(githubTransient.commanderAction ?? "").includes("keep the task running"), "GitHub transient action should preserve fresh-heartbeat tasks", githubTransient);
const githubTransientFullRecord = asRecord(await codexPrPreflightQueryForTest(["--remote", "--full"], {
config: null,
coreFetch: () => ({
ok: true,
status: 200,
body: {
runtimePreflight: rawRuntimePreflightFixture({
ok: false,
pullRequestDelivery: {
...asRecord(rawRuntimePreflightFixture().pullRequestDelivery),
ok: false,
credentials: {
ghTokenPresent: true,
githubTokenPresent: false,
ghHostsConfigPresent: false,
gitCredentialsPresent: false,
},
egress: {
proxy: {
selectedProxyHost: "d601-provider-egress-proxy.unidesk.svc.cluster.local",
selectedProxyPort: "18789",
selectedProxyHostResolvable: true,
},
githubDefault: { command: "curl", args: ["-IsS", "https://github.com"], ok: false, exitCode: 6, signal: null, error: null, stdout: "", stderr: "curl: (6) Could not resolve host: github.com" },
apiDefault: { command: "curl", args: ["-IsS", "https://api.github.com"], ok: false, exitCode: 6, signal: null, error: null, stdout: "", stderr: "curl: (6) Could not resolve host: api.github.com" },
issueApi: null,
},
remote: {
gitLsRemote: { command: "git", args: ["ls-remote", "--heads", "origin", "master"], ok: false, exitCode: 128, signal: null, error: null, stdout: "", stderr: "ssh: Could not resolve hostname github.com: Temporary failure in name resolution" },
gitHttpsLsRemote: null,
githubSshAuthenticated: false,
ghAuthStatus: { command: "gh", args: ["auth", "status"], ok: false, exitCode: 1, signal: null, error: null, stdout: "", stderr: "error connecting to api.github.com" },
ghRepoView: null,
ghIssueView: null,
ghPrReadOnly: null,
},
limitations: [
"GitHub HTTPS probe failed with the default environment/proxy",
"GitHub API probe failed with the default environment/proxy",
"git ls-remote origin master failed",
],
risks: [],
},
}),
},
}),
}), "github transient full record");
const githubTransientPreflight = asRecord(githubTransientFullRecord.preflight);
assertCondition(githubTransientPreflight.retryable === true, "GitHub transient full preflight should be retryable", githubTransientPreflight);
assertCondition(githubTransientPreflight.commanderAction === "retry-backoff-or-keep-running-if-heartbeat-fresh", "GitHub transient full preflight should expose bounded commander action", githubTransientPreflight);
let observedDryRunPath = "";
const dryRunContract = await codexPrPreflightQueryForTest([
@@ -707,24 +759,23 @@ async function main(): Promise<void> {
assertCondition(observedDryRunPath === "/api/microservices/code-queue/proxy/api/runtime-preflight?remote=1&pushDryRun=1&pushDryRunRef=refs%2Fheads%2Fprobe%2Fcode-queue-pr-capability&prCreateDryRun=1&prCreateDryRunHead=code-queue%2Fissue-35-pr-dry-run-probe&issue=20", "combined dry-run query should pass all requested guards", { observedDryRunPath });
const dryRunRecord = asRecord(dryRunContract);
assertCondition(dryRunRecord.failureKind === "auth-missing", "missing runner token should remain auth-missing even when system gh is absent", dryRunRecord);
const dryRunPreflight = asRecord(dryRunRecord.preflight);
const dryRunAuthBroker = asRecord(dryRunPreflight.authBroker);
const dryRunScopeBoundary = asRecord(dryRunPreflight.scopeBoundary);
const dryRunActiveRunner = asRecord(dryRunPreflight.activeRunnerDevContainer);
assertCondition(dryRunRecord.preflight === undefined, "combined dry-run default output should omit detailed preflight", dryRunRecord);
const dryRunSchedulerPreflight = asRecord(dryRunRecord.schedulerPreflight);
const dryRunAuthBroker = asRecord(dryRunSchedulerPreflight.authBroker);
const dryRunScopeBoundary = asRecord(dryRunRecord.scopeBoundary);
const dryRunActiveRunner = asRecord(dryRunRecord.activeRunnerPrCapability);
assertCondition(dryRunAuthBroker.source === "broker/auth-broker-needed", "missing runner token should expose broker/auth-broker-needed", dryRunAuthBroker);
assertCondition(dryRunAuthBroker.degradedReason === "auth-broker-needed", "auth broker degraded reason should be explicit", dryRunAuthBroker);
assertCondition(dryRunSchedulerPreflight.degradedReason === "auth-broker-needed", "auth broker degraded reason should be explicit", dryRunSchedulerPreflight);
assertCondition(dryRunScopeBoundary.scopesAreIndependent === true, "local compact preflight should expose independent auth scopes", dryRunScopeBoundary);
assertCondition(dryRunActiveRunner.scope === "current-cli-process", "local compact preflight should expose current CLI process capability", dryRunActiveRunner);
const dryRunBrokerEvidence = asRecord(dryRunAuthBroker.evidence);
assertCondition(dryRunBrokerEvidence.systemGhBinaryOk === false, "system gh absence should be reported separately", dryRunBrokerEvidence);
assertCondition(dryRunBrokerEvidence.unideskGhCliOk === true, "UniDesk REST gh CLI should not be marked unavailable because system gh is missing", dryRunBrokerEvidence);
assertCondition(dryRunBrokerEvidence.systemGhMissingMisclassifiedAsUniDeskCliMissing === false, "system gh absence must not be misclassified", dryRunBrokerEvidence);
const dryRunPrContract = asRecord(dryRunPreflight.prCapabilityContract);
assertCondition(dryRunActiveRunner.scope === "current-cli-process", "compact default should expose current CLI process capability", dryRunActiveRunner);
const dryRunPrContract = asRecord(dryRunRecord.prCapability);
assertCondition(dryRunPrContract.systemGhBinaryRequiredForWrites === false, "system gh absence must not be required for UniDesk REST gh writes", dryRunPrContract);
assertCondition(dryRunPrContract.unideskGhCliOk === true, "UniDesk REST gh CLI should not be marked unavailable because system gh is missing", dryRunPrContract);
assertCondition(asRecord(dryRunPrContract.pushDryRun).requested === true, "push dry-run should be requested", dryRunPrContract);
assertCondition(asRecord(dryRunPrContract.pushDryRun).writesRemote === false, "push dry-run must be marked non-writing", dryRunPrContract);
assertCondition(asRecord(dryRunPrContract.prCreateDryRun).requested === true, "PR create dry-run should be requested", dryRunPrContract);
assertCondition(asRecord(dryRunPrContract.prCreateDryRun).writesRemote === false, "PR create dry-run must be marked non-writing", dryRunPrContract);
assertCondition(asRecord(dryRunPrContract.prCreateDryRun).headBranch === "code-queue/issue-35-pr-dry-run-probe", "PR dry-run head should come from the option", dryRunPrContract);
assertCondition(dryRunPrContract.sourceBranch === "code-queue/issue-35-pr-dry-run-probe", "PR dry-run head should come from the option", dryRunPrContract);
const brokerIssuedContract = await codexPrPreflightQueryForTest(["--remote"], {
config: null,
@@ -768,18 +819,17 @@ async function main(): Promise<void> {
});
const brokerIssuedRecord = asRecord(brokerIssuedContract);
assertCondition(brokerIssuedRecord.ok === true, "broker-issued token branch should be ready", brokerIssuedRecord);
const brokerIssuedPreflight = asRecord(brokerIssuedRecord.preflight);
const brokerIssuedTokenCoverage = asRecord(brokerIssuedPreflight.tokenCoverage);
const brokerIssuedAuthBroker = asRecord(brokerIssuedPreflight.authBroker);
const brokerIssuedCapability = asRecord(brokerIssuedAuthBroker.capability);
const brokerIssuedPrContract = asRecord(brokerIssuedPreflight.prCapabilityContract);
assertCondition(brokerIssuedTokenCoverage.source === "auth-broker", "broker-issued branch should use auth-broker token coverage", brokerIssuedTokenCoverage);
assertCondition(brokerIssuedTokenCoverage.credentialSource === "broker-issued-token", "broker-issued branch should expose broker-issued-token capability", brokerIssuedTokenCoverage);
assertCondition(brokerIssuedRecord.preflight === undefined, "broker-issued default output should omit detailed preflight", brokerIssuedRecord);
const brokerIssuedScheduler = asRecord(brokerIssuedRecord.schedulerPreflight);
const brokerIssuedAuthBroker = asRecord(brokerIssuedScheduler.authBroker);
const brokerIssuedPrContract = asRecord(brokerIssuedRecord.prCapability);
assertCondition(brokerIssuedScheduler.authSource === "auth-broker", "broker-issued branch should use auth-broker token coverage", brokerIssuedScheduler);
assertCondition(brokerIssuedScheduler.credentialSource === "broker-issued-token", "broker-issued branch should expose broker-issued-token capability", brokerIssuedScheduler);
assertCondition(brokerIssuedAuthBroker.source === "auth-broker", "broker-issued branch should expose authBroker.source", brokerIssuedAuthBroker);
assertCondition(brokerIssuedAuthBroker.nextAction === "use-auth-broker", "broker-issued branch should expose nextAction", brokerIssuedAuthBroker);
assertCondition(brokerIssuedCapability.systemGhBinaryRequiredForWrites === false, "broker-issued branch should not require system gh binary", brokerIssuedCapability);
assertCondition(brokerIssuedCapability.realPrCreateRequiresCommanderAuthorization === true, "real PR creation should still require commander authorization", brokerIssuedCapability);
assertCondition(asRecord(brokerIssuedPrContract.authBroker).source === "auth-broker", "PR capability should include broker source", brokerIssuedPrContract);
assertCondition(brokerIssuedAuthBroker.capabilitySource === "broker-issued-token", "broker-issued branch should expose broker-issued capability", brokerIssuedAuthBroker);
assertCondition(brokerIssuedPrContract.systemGhBinaryRequiredForWrites === false, "broker-issued branch should not require system gh binary", brokerIssuedPrContract);
assertCondition(brokerIssuedPrContract.realPrCreateRequiresCommanderAuthorization === true, "real PR creation should still require commander authorization", brokerIssuedPrContract);
const envTokenContract = await codexPrPreflightQueryForTest(["--remote"], {
config: null,
@@ -829,11 +879,11 @@ async function main(): Promise<void> {
});
const envTokenRecord = asRecord(envTokenContract);
assertCondition(envTokenRecord.ok === true, "env token branch should be ready", envTokenRecord);
const envTokenPreflight = asRecord(envTokenRecord.preflight);
const envTokenCoverage = asRecord(envTokenPreflight.tokenCoverage);
const envTokenAuthBroker = asRecord(envTokenPreflight.authBroker);
assertCondition(envTokenCoverage.source === "GH_TOKEN", "env token branch should expose GH_TOKEN source", envTokenCoverage);
assertCondition(envTokenCoverage.credentialSource === "env-token", "env token branch should expose env-token capability", envTokenCoverage);
assertCondition(envTokenRecord.preflight === undefined, "env-token default output should omit detailed preflight", envTokenRecord);
const envTokenScheduler = asRecord(envTokenRecord.schedulerPreflight);
const envTokenAuthBroker = asRecord(envTokenScheduler.authBroker);
assertCondition(envTokenScheduler.authSource === "GH_TOKEN", "env token branch should expose GH_TOKEN source", envTokenScheduler);
assertCondition(envTokenScheduler.credentialSource === "env-token", "env token branch should expose env-token capability", envTokenScheduler);
assertCondition(envTokenAuthBroker.source === "GH_TOKEN", "env token branch should not pretend broker is configured", envTokenAuthBroker);
assertCondition(envTokenAuthBroker.nextAction === "use-env-token-until-auth-broker-live", "env token branch should still point at broker migration", envTokenAuthBroker);
@@ -852,25 +902,25 @@ async function main(): Promise<void> {
const missingTokenTopSummary = asRecord(missingTokenRecord.authScopeSummary);
const missingTokenTopScopeBoundary = asRecord(missingTokenRecord.scopeBoundary);
const missingTokenTopActions = Array.isArray(missingTokenRecord.recommendedActions) ? missingTokenRecord.recommendedActions : [];
const missingTokenPreflight = asRecord(missingTokenRecord.preflight);
const missingTokenAuthBroker = asRecord(missingTokenPreflight.authBroker);
const missingTokenSummary = asRecord(missingTokenPreflight.authScopeSummary);
const missingTokenScopeBoundary = asRecord(missingTokenPreflight.scopeBoundary);
const missingTokenActiveRunner = asRecord(missingTokenPreflight.activeRunnerDevContainer);
const missingTokenActions = Array.isArray(missingTokenPreflight.recommendedActions) ? missingTokenPreflight.recommendedActions : [];
const missingTokenCapability = asRecord(missingTokenAuthBroker.capability);
assertCondition(missingTokenRecord.preflight === undefined, "missing-token default output should omit detailed preflight", missingTokenRecord);
const missingTokenScheduler = asRecord(missingTokenRecord.schedulerPreflight);
const missingTokenAuthBroker = asRecord(missingTokenScheduler.authBroker);
const missingTokenScopeBoundary = asRecord(missingTokenRecord.scopeBoundary);
const missingTokenActiveRunner = asRecord(missingTokenRecord.activeRunnerPrCapability);
const missingTokenActions = Array.isArray(missingTokenRecord.recommendedActions) ? missingTokenRecord.recommendedActions : [];
const missingTokenPrCapability = asRecord(missingTokenRecord.prCapability);
assertCondition(missingTokenTopSummary.schedulerAuthMissingIsScoped === true, "missing-token top-level summary should expose scoped scheduler auth missing", missingTokenTopSummary);
assertCondition(missingTokenTopScopeBoundary.schedulerAuthMissingDoesNotMeanActiveRunnerCannotCreatePr === true, "missing-token top-level boundary should be prominent", missingTokenTopScopeBoundary);
assertCondition(Array.isArray(missingTokenRecord.recommendedActions) && missingTokenTopActions.length === 3, "missing-token top-level recommended actions should stay bounded", missingTokenRecord.recommendedActions);
assertCondition(missingTokenAuthBroker.source === "broker/auth-broker-needed", "missing-token branch should expose broker/auth-broker-needed", missingTokenAuthBroker);
assertCondition(missingTokenAuthBroker.nextAction === "configure-auth-broker-or-env-token", "missing-token branch should expose nextAction", missingTokenAuthBroker);
assertCondition(missingTokenCapability.source === "missing-token", "missing-token branch should expose missing-token capability", missingTokenCapability);
assertCondition(missingTokenCapability.systemGhBinaryRequiredForWrites === false, "missing-token branch should still not require system gh binary for UniDesk gh CLI", missingTokenCapability);
assertCondition(missingTokenSummary.schedulerAuthMissingIsScoped === true, "missing-token compact preflight should expose scoped scheduler auth missing", missingTokenSummary);
assertCondition(missingTokenAuthBroker.capabilitySource === "missing-token", "missing-token branch should expose missing-token capability", missingTokenAuthBroker);
assertCondition(missingTokenPrCapability.systemGhBinaryRequiredForWrites === false, "missing-token branch should still not require system gh binary for UniDesk gh CLI", missingTokenPrCapability);
assertCondition(missingTokenTopSummary.schedulerAuthMissingIsScoped === true, "missing-token compact summary should expose scoped scheduler auth missing", missingTokenTopSummary);
assertCondition(String(missingTokenScopeBoundary.currentRunnerCheck ?? "").includes("gh auth status"), "missing-token branch should point to active runner auth check", missingTokenScopeBoundary);
assertCondition(String(missingTokenScopeBoundary.currentRunnerCheck ?? "").includes("gh pr create --dry-run"), "missing-token branch should point to active runner PR create dry-run", missingTokenScopeBoundary);
assertCondition(missingTokenActiveRunner.relationToRemotePreflight === "independent-scope; scheduler-runner-env auth-missing does not prove the active runner/dev container lacks GitHub PR capability", "missing-token branch should not overstate active runner PR capability", missingTokenActiveRunner);
assertCondition(Array.isArray(missingTokenPreflight.recommendedActions) && missingTokenActions.length === 3, "missing-token compact recommended actions should stay bounded", missingTokenPreflight.recommendedActions);
assertCondition(missingTokenActiveRunner.independentOfSchedulerPreflight === true, "missing-token branch should not overstate active runner PR capability", missingTokenActiveRunner);
assertCondition(Array.isArray(missingTokenRecord.recommendedActions) && missingTokenActions.length === 3, "missing-token compact recommended actions should stay bounded", missingTokenRecord.recommendedActions);
assertCondition(missingTokenActions.some((action) => String(asRecord(action).command ?? "").includes("gh auth status")), "missing-token branch should recommend gh auth status", missingTokenActions);
assertCondition(missingTokenActions.some((action) => String(asRecord(action).command ?? "").includes("gh pr create") && asRecord(action).writesRemote === false), "missing-token branch should recommend PR create dry-run without writes", missingTokenActions);
@@ -118,7 +118,7 @@ assertCondition(microserviceCli.includes("compactSkillSync"), "microservice heal
assertCondition(helpSource.includes("codex skills-sync --dry-run"), "CLI help must document the skills sync dry-run command");
assertCondition(docsReference.includes("codex skills-sync --dry-run"), "reference docs must document the skills sync dry-run command");
const preflightSummary = asRecord(codexPrPreflightQueryForTest(["--remote"], {
const skillsPreflightTransport = {
config: null,
coreFetch: () => ({
ok: true,
@@ -169,18 +169,26 @@ const preflightSummary = asRecord(codexPrPreflightQueryForTest(["--remote"], {
},
},
}),
}), "preflight summary");
};
const defaultPreflightSummary = asRecord(codexPrPreflightQueryForTest(["--remote"], skillsPreflightTransport), "default preflight summary");
assertCondition(defaultPreflightSummary.failureKind === "runner-skills-blocker", "default preflight should classify missing skills as runner-skills-blocker", defaultPreflightSummary);
assertCondition(defaultPreflightSummary.degradedReason === "unapproved-target", "default preflight degraded reason should use the skills sync blocker first", defaultPreflightSummary);
assertCondition(defaultPreflightSummary.preflight === undefined, "default PR preflight should omit detailed preflight internals", defaultPreflightSummary);
assertCondition(asRecord(defaultPreflightSummary.disclosure, "defaultPreflightSummary.disclosure").fullDetailOmitted === true, "default PR preflight should disclose full detail omission", defaultPreflightSummary.disclosure);
assertCondition(String(asRecord(defaultPreflightSummary.disclosure, "defaultPreflightSummary.disclosure").expandWith ?? "").includes("--full"), "default PR preflight should point to --full expansion", defaultPreflightSummary.disclosure);
const preflightSummary = asRecord(codexPrPreflightQueryForTest(["--remote", "--full"], skillsPreflightTransport), "full preflight summary");
const preflight = asRecord(preflightSummary.preflight, "preflight");
const preflightSkills = asRecord(preflight.skills, "preflight.skills");
const preflightSkillsSync = asRecord(preflight.skillsSync, "preflight.skillsSync");
assertCondition(preflightSummary.failureKind === "runner-skills-blocker", "compact preflight should classify missing skills as runner-skills-blocker", preflightSummary);
assertCondition(preflightSummary.degradedReason === "unapproved-target", "compact preflight degraded reason should use the skills sync blocker first", preflightSummary);
assertCondition(preflightSkills.target === "/path/that/does/not/exist/for-code-queue-skills-test", "compact preflight must show skills target", preflightSkills);
assertCondition(preflightSkillsSync.dryRun === true && preflightSkillsSync.mutation === false, "compact preflight must show non-mutating skills sync dry-run", preflightSkillsSync);
assertCondition(asRecord(preflightSkillsSync.counts, "preflight.skillsSync.counts").missingTargetSkills === 2, "compact preflight must show missing target count", preflightSkillsSync);
assertCondition(asRecord(preflightSkillsSync.plannedActions, "preflight.skillsSync.plannedActions").copy === false, "compact preflight must show no copy action", preflightSkillsSync);
assertCondition(preflightSkillsSync.valuesPrinted === false, "compact preflight skills sync must declare valuesPrinted=false", preflightSkillsSync);
assertCondition(!JSON.stringify(preflightSkillsSync).includes(forbiddenPathLiteral), "compact preflight must not propagate misspelled path literal");
assertCondition(preflightSummary.failureKind === "runner-skills-blocker", "full preflight should classify missing skills as runner-skills-blocker", preflightSummary);
assertCondition(preflightSummary.degradedReason === "unapproved-target", "full preflight degraded reason should use the skills sync blocker first", preflightSummary);
assertCondition(preflightSkills.target === "/path/that/does/not/exist/for-code-queue-skills-test", "full preflight must show skills target", preflightSkills);
assertCondition(preflightSkillsSync.dryRun === true && preflightSkillsSync.mutation === false, "full preflight must show non-mutating skills sync dry-run", preflightSkillsSync);
assertCondition(asRecord(preflightSkillsSync.counts, "preflight.skillsSync.counts").missingTargetSkills === 2, "full preflight must show missing target count", preflightSkillsSync);
assertCondition(asRecord(preflightSkillsSync.plannedActions, "preflight.skillsSync.plannedActions").copy === false, "full preflight must show no copy action", preflightSkillsSync);
assertCondition(preflightSkillsSync.valuesPrinted === false, "full preflight skills sync must declare valuesPrinted=false", preflightSkillsSync);
assertCondition(!JSON.stringify(preflightSkillsSync).includes(forbiddenPathLiteral), "full preflight must not propagate misspelled path literal");
const healthSummary = asRecord(summarizeMicroserviceObservation("health", "code-queue", {
ok: true,
+209 -10
View File
@@ -4180,9 +4180,193 @@ function prPreflightAuthScopeSummary(tokenCoverage: Record<string, unknown> | nu
};
}
function prPreflightTokenCoverage(record: Record<string, unknown>): Record<string, unknown> | null {
const preflight = asRecord(record.preflight);
const schedulerPreflight = asRecord(record.schedulerPreflight);
const schedulerAuth = asRecord(schedulerPreflight?.auth);
const schedulerSummary = schedulerPreflight === null ? null : {
ok: schedulerPreflight.authReady ?? null,
source: schedulerPreflight.authSource ?? null,
credentialSource: schedulerPreflight.credentialSource ?? null,
scope: schedulerPreflight.scope ?? null,
missing: Array.isArray(schedulerPreflight.missing) && schedulerPreflight.missing.length > 0
? schedulerPreflight.missing.map(String)
: schedulerPreflight.authReady === false
? ["GH_TOKEN", "GITHUB_TOKEN"]
: [],
runnerDisposition: schedulerPreflight.authReady === true ? "ready" : "infra-blocked",
};
return asRecord(record.tokenCoverage)
?? asRecord(preflight?.tokenCoverage)
?? schedulerAuth
?? schedulerSummary
?? null;
}
function prPreflightAuthBroker(record: Record<string, unknown>): Record<string, unknown> | null {
const preflight = asRecord(record.preflight);
const schedulerPreflight = asRecord(record.schedulerPreflight);
return asRecord(record.authBroker)
?? asRecord(preflight?.authBroker)
?? asRecord(schedulerPreflight?.authBroker)
?? null;
}
function prPreflightCapabilityContract(record: Record<string, unknown>): Record<string, unknown> | null {
const preflight = asRecord(record.preflight);
const prCapability = asRecord(record.prCapability);
return asRecord(record.prCapabilityContract)
?? asRecord(preflight?.prCapabilityContract)
?? prCapability
?? null;
}
function prPreflightCommandSet(record: Record<string, unknown>, options: CodexPrPreflightOptions): Record<string, unknown> {
const preflight = asRecord(record.preflight);
const commands = asRecord(record.commands) ?? asRecord(preflight?.commands) ?? {};
const activeRunnerDevContainer = asRecord(record.activeRunnerDevContainer) ?? activeRunnerDevContainerCapability();
const activeCommands = asRecord(activeRunnerDevContainer.commands) ?? {};
const remoteFlag = options.remote ? " --remote" : "";
const fullDetail = `bun scripts/cli.ts codex pr-preflight${remoteFlag} --full`;
return {
verifyActiveRunnerAuth: activeCommands.authStatus ?? commands.local ?? "bun scripts/cli.ts gh auth status --repo pikasTech/unidesk",
verifyActiveRunnerPrCreateDryRun: activeCommands.prCreateDryRun ?? "bun scripts/cli.ts gh pr create --repo pikasTech/unidesk --title <title> --body-file <file> --base master --head <head> --dry-run",
rerunSchedulerPreflight: commands.runner ?? `bun scripts/cli.ts codex pr-preflight${remoteFlag}`,
fullDetail,
rawProxy: commands.rawProxy ?? "bun scripts/cli.ts microservice proxy code-queue /api/runtime-preflight?remote=1 --raw --full",
schedulerAuthSource: "configure auth-broker or inject GH_TOKEN/GITHUB_TOKEN into the scheduler runtime secret",
};
}
function compactRecommendedActions(record: Record<string, unknown>): Record<string, unknown>[] {
const actions = Array.isArray(record.recommendedActions) ? record.recommendedActions : [];
if (actions.length > 0) {
return actions.slice(0, 3).map((item) => {
const action = asRecord(item) ?? {};
return {
scope: action.scope ?? null,
priority: action.priority ?? null,
action: action.action ?? null,
command: action.command ?? null,
writesRemote: action.writesRemote ?? false,
};
});
}
const tokenCoverage = prPreflightTokenCoverage(record);
return prPreflightRecommendedActions(tokenCoverage);
}
function compactPrPreflightCommanderView(record: Record<string, unknown>, options: CodexPrPreflightOptions): Record<string, unknown> {
if (options.full) return record;
const tokenCoverage = prPreflightTokenCoverage(record);
const authBroker = prPreflightAuthBroker(record);
const capability = prPreflightCapabilityContract(record);
const activeRunnerDevContainer = asRecord(record.activeRunnerDevContainer) ?? activeRunnerDevContainerCapability();
const activeCommands = asRecord(activeRunnerDevContainer.commands) ?? {};
const authBrokerCapability = asRecord(authBroker?.capability);
const expectedPrHandoff = asRecord(capability?.expectedPrHandoff);
const unideskGhCli = asRecord(capability?.unideskGhCli);
const pushDryRun = asRecord(capability?.pushDryRun);
const prCreateDryRun = asRecord(capability?.prCreateDryRun);
const unsupportedMergeBoundary = asRecord(capability?.unsupportedMergeBoundary);
const commands = prPreflightCommandSet(record, options);
const schedulerAuthReady = tokenCoverage?.ok === true;
const activeRunnerTokenCandidatePresent = activeRunnerDevContainer.ok === true;
const failureKind = record.failureKind ?? (schedulerAuthReady ? null : "auth-missing");
const degradedReason = record.degradedReason ?? (schedulerAuthReady ? null : "auth-broker-needed");
const githubTransient = asRecord(record.githubTransient);
return {
ok: record.ok === true,
runnerDisposition: record.runnerDisposition ?? (record.ok === true ? "ready" : "infra-blocked"),
failureKind,
degradedReason,
...(record.retryable === true ? { retryable: true } : {}),
...(typeof record.commanderAction === "string" ? { commanderAction: record.commanderAction } : {}),
...(githubTransient === null ? {} : { githubTransient }),
summary: {
status: record.ok === true ? "ready" : "blocked",
schedulerPreflightAuthReady: schedulerAuthReady,
schedulerPreflightScope: tokenCoverage?.scope ?? "scheduler-runner-env",
activeRunnerTokenCandidatePresent,
activeRunnerScope: activeRunnerDevContainer.scope ?? "current-cli-process",
interpretation: schedulerAuthReady
? "scheduler preflight auth is ready; still use active-runner dry-runs before writes"
: "scheduler auth is missing for preflight admission only; this does not prove the active runner/dev container cannot create or comment PRs",
},
schedulerPreflight: {
scope: tokenCoverage?.scope ?? "scheduler-runner-env",
authReady: schedulerAuthReady,
authSource: tokenCoverage?.source ?? null,
credentialSource: tokenCoverage?.credentialSource ?? null,
missing: Array.isArray(tokenCoverage?.missing) ? tokenCoverage.missing.map(String) : [],
failureKind: schedulerAuthReady ? null : failureKind,
degradedReason: schedulerAuthReady ? null : degradedReason,
authBroker: authBroker === null ? null : {
ok: authBroker.ok ?? schedulerAuthReady,
source: authBroker.source ?? null,
configured: authBroker.configured ?? null,
needed: authBroker.needed ?? !schedulerAuthReady,
nextAction: authBroker.nextAction ?? null,
capabilitySource: authBrokerCapability?.source ?? tokenCoverage?.credentialSource ?? null,
},
},
activeRunnerPrCapability: {
scope: activeRunnerDevContainer.scope ?? "current-cli-process",
tokenCandidatePresent: activeRunnerTokenCandidatePresent,
credentialSource: activeRunnerDevContainer.credentialSource ?? null,
ghTokenPresent: activeRunnerDevContainer.ghTokenPresent ?? false,
githubTokenPresent: activeRunnerDevContainer.githubTokenPresent ?? false,
independentOfSchedulerPreflight: activeRunnerDevContainer.notEquivalentToSchedulerEnv ?? true,
verifyCommands: {
authStatus: activeCommands.authStatus ?? commands.verifyActiveRunnerAuth,
prCreateDryRun: activeCommands.prCreateDryRun ?? commands.verifyActiveRunnerPrCreateDryRun,
},
},
prCapability: capability === null ? null : {
targetBranch: capability.targetBranch ?? "master",
sourceBranch: expectedPrHandoff?.sourceBranch ?? prCreateDryRun?.headBranch ?? null,
unideskGhCliOk: unideskGhCli?.ok ?? null,
systemGhBinaryRequiredForWrites: capability.systemGhBinaryRequiredForWrites ?? false,
realPrCreateRequiresCommanderAuthorization: capability.realPrCreateRequiresCommanderAuthorization ?? true,
pushDryRun: pushDryRun === null ? null : {
requested: pushDryRun.requested ?? false,
writesRemote: pushDryRun.writesRemote ?? false,
commandShape: pushDryRun.commandShape ?? null,
},
prCreateDryRun: prCreateDryRun === null ? null : {
requested: prCreateDryRun.requested ?? false,
writesRemote: prCreateDryRun.writesRemote ?? false,
commandShape: prCreateDryRun.commandShape ?? null,
},
mergeSupported: unsupportedMergeBoundary?.supported ?? false,
mergeCommand: unsupportedMergeBoundary?.command ?? "bun scripts/cli.ts gh pr merge <number> --repo pikasTech/unidesk",
},
authScopeSummary: record.authScopeSummary ?? prPreflightAuthScopeSummary(tokenCoverage, activeRunnerDevContainer),
scopeBoundary: record.scopeBoundary ?? prPreflightScopeBoundary(tokenCoverage),
recommendedActions: compactRecommendedActions(record),
upstream: record.upstream ?? null,
controlPlane: record.controlPlane ?? null,
observationGap: record.observationGap ?? undefined,
localObservationGap: record.localObservationGap ?? undefined,
localObservationSummary: record.localObservationSummary ?? undefined,
remoteObservationSummary: record.remoteObservationSummary ?? undefined,
commands,
disclosure: {
defaultView: "commander-compact",
fullDetailOmitted: true,
fullObservationsOmitted: asRecord(record.disclosure)?.fullObservationsOmitted ?? true,
expandWith: commands.fullDetail,
rawProxy: commands.rawProxy,
detailFieldsOmitted: ["preflight", "tools", "agentPorts", "git", "egress", "remote", "limitations", "risks", "rawRuntimePreflight"],
},
};
}
function decoratePrPreflightScopeBoundary(record: Record<string, unknown>): Record<string, unknown> {
const preflight = asRecord(record.preflight);
const tokenCoverage = asRecord(record.tokenCoverage) ?? asRecord(preflight?.tokenCoverage);
const tokenCoverage = prPreflightTokenCoverage(record);
const scopeBoundary = prPreflightScopeBoundary(tokenCoverage);
const activeRunnerDevContainer = activeRunnerDevContainerCapability();
const authScopeSummary = prPreflightAuthScopeSummary(tokenCoverage, activeRunnerDevContainer);
@@ -4224,7 +4408,20 @@ function prPreflightObservationGap(kind: Exclude<CodeQueueObservationGapKind, nu
function prPreflightObservationSummary(record: Record<string, unknown> | null): Record<string, unknown> | null {
if (record === null) return null;
const preflight = asRecord(record.preflight);
const tokenCoverage = asRecord(record.tokenCoverage) ?? asRecord(preflight?.tokenCoverage);
const schedulerPreflight = asRecord(record.schedulerPreflight);
const tokenCoverage = asRecord(record.tokenCoverage)
?? asRecord(preflight?.tokenCoverage)
?? (schedulerPreflight === null ? null : {
ok: schedulerPreflight.authReady ?? null,
source: schedulerPreflight.authSource ?? null,
credentialSource: schedulerPreflight.credentialSource ?? null,
scope: schedulerPreflight.scope ?? null,
missing: Array.isArray(schedulerPreflight.missing) && schedulerPreflight.missing.length > 0
? schedulerPreflight.missing.map(String)
: schedulerPreflight.authReady === false
? ["GH_TOKEN", "GITHUB_TOKEN"]
: [],
});
const controlPlane = asRecord(record.controlPlane);
const targetStack = asRecord(record.targetStack);
return {
@@ -4561,7 +4758,7 @@ function codeQueuePrPreflight(optionArgs: string[] = [], transport: CodeQueuePrP
const remoteRecord = asRecord(remoteResponse);
if (remoteRecord !== null) {
if (remoteRecord.ok === false) {
return decoratePrPreflightScopeBoundary({
return compactPrPreflightCommanderView(decoratePrPreflightScopeBoundary({
...remoteRecord,
observationGap: prPreflightObservationGap(
remoteRecord.failureKind === "control-plane-missing" ? "control-plane-observation-gap" : "runner-local-observation-gap",
@@ -4584,9 +4781,9 @@ function codeQueuePrPreflight(optionArgs: string[] = [], transport: CodeQueuePrP
remoteFallbackUsed: true,
},
...maybeFullPrPreflightObservations(options, localRecord, remoteRecord),
});
}), options);
}
return decoratePrPreflightScopeBoundary({
return compactPrPreflightCommanderView(decoratePrPreflightScopeBoundary({
...remoteRecord,
localObservationGap: prPreflightObservationGap("runner-local-observation-gap", {
reason: "local backend-core target-stack absence was bypassed by healthy remote control-plane fallback",
@@ -4603,7 +4800,7 @@ function codeQueuePrPreflight(optionArgs: string[] = [], transport: CodeQueuePrP
remoteFallbackUsed: true,
},
...maybeFullPrPreflightObservations(options, localRecord, remoteRecord),
});
}), options);
}
}
if (localRecord?.ok !== true) {
@@ -4693,13 +4890,14 @@ function codeQueuePrPreflight(optionArgs: string[] = [], transport: CodeQueuePrP
};
}
const compact = compactPrRuntimePreflight(preflight, options);
return {
return compactPrPreflightCommanderView({
ok: compact.ok,
runnerDisposition: compact.runnerDisposition,
failureKind: compact.failureKind ?? null,
degradedReason: compact.degradedReason ?? null,
...(compact.retryable === true ? { retryable: true } : {}),
...(typeof compact.commanderAction === "string" ? { commanderAction: compact.commanderAction } : {}),
...(asRecord(compact.githubTransient) === null ? {} : { githubTransient: compact.githubTransient }),
authScopeSummary: compact.authScopeSummary,
scopeBoundary: compact.scopeBoundary,
activeRunnerDevContainer: compact.activeRunnerDevContainer,
@@ -4711,7 +4909,7 @@ function codeQueuePrPreflight(optionArgs: string[] = [], transport: CodeQueuePrP
remoteFallbackUsed: false,
},
preflight: compact,
};
}, options);
}
export function codexPrPreflightQueryForTest(optionArgs: string[], transport: CodeQueuePrPreflightTransport = {}): unknown {
@@ -4751,13 +4949,14 @@ export async function codexPrPreflightQueryAsync(optionArgs: string[], fetcher:
};
}
const compact = compactPrRuntimePreflight(preflight, options);
return {
return compactPrPreflightCommanderView({
ok: compact.ok,
runnerDisposition: compact.runnerDisposition,
failureKind: compact.failureKind ?? null,
degradedReason: compact.degradedReason ?? null,
...(compact.retryable === true ? { retryable: true } : {}),
...(typeof compact.commanderAction === "string" ? { commanderAction: compact.commanderAction } : {}),
...(asRecord(compact.githubTransient) === null ? {} : { githubTransient: compact.githubTransient }),
authScopeSummary: compact.authScopeSummary,
scopeBoundary: compact.scopeBoundary,
activeRunnerDevContainer: compact.activeRunnerDevContainer,
@@ -4769,7 +4968,7 @@ export async function codexPrPreflightQueryAsync(optionArgs: string[], fetcher:
remoteFallbackUsed: false,
},
preflight: compact,
};
}, options);
}
export function codexSubmitRoutingRecommendationForTest(prompt: string, model?: string): SubmitRoutingRecommendation {
+2 -2
View File
@@ -54,7 +54,7 @@ export function rootHelp(): unknown {
{ command: "codex deploy <commitId> [--provider-id D601] [--timeout-ms N]", description: "Disabled legacy Code Queue deploy path; use the dev-only artifact consumer instead." },
{ command: "codex submit [prompt] [--prompt-file path|--prompt-stdin] [--queue queueId] [--provider-id id] [--cwd path] [--model model] [--execution-mode mode] [--max-attempts N] [--reference-task-id id] [--dry-run]", description: "Submit a Code Queue task through backend-core -> code-queue proxy; --dry-run shows the structured request, while real success only confirms the write and task id." },
{ command: "codex skills-sync --dry-run [--full]", description: "Inspect the controlled runner skills hostPath lifecycle contract without copying files, restarting services, reading secrets, or mutating live runner paths." },
{ command: "codex pr-preflight [--remote] [--push-dry-run --push-dry-run-ref refs/heads/probe/<name>] [--pr-create-dry-run --pr-create-dry-run-head <head>] [--issue N]", description: "Read-only PR admission check against the D601 scheduler/runner token, GitHub egress, repo visibility, skills lifecycle health, optional push dry-run, and PR body/create dry-run guard." },
{ command: "codex pr-preflight [--remote] [--push-dry-run --push-dry-run-ref refs/heads/probe/<name>] [--pr-create-dry-run --pr-create-dry-run-head <head>] [--issue N] [--full|--raw]", description: "Read-only PR admission check with compact commander output by default; use --full or --raw to expand the full runtime preflight, tool, and observation payload." },
{ command: "codex task <taskId> [--detail] [--trace --tail|--from-start|--after-seq N|--before-seq N --limit N] [--full]", description: "Fetch the bounded review view by default; --detail is still capped, while --full/trace/output explicitly expand evidence." },
{ command: "codex tasks [--view supervisor|full] [--queue id] [--status status[,status]] [--unread|--unread-only] [--limit N] [--before-id id]", description: "Show the low-noise supervisor view by default: compact task rows, tiny local sections, activity counts, diagnostics, and drill-down commands; use --view full for detailed rows." },
{ command: "codex output <taskId> [--tail|--from-start|--after-seq N|--before-seq N --limit N] [--full-text]", description: "Fetch paged raw Code Queue output records; default caps large limits/text previews, --full-text explicitly expands one seq window." },
@@ -258,7 +258,7 @@ function codexHelp(): unknown {
"bun scripts/cli.ts codex read <taskId>",
"bun scripts/cli.ts codex dev-ready",
"bun scripts/cli.ts codex skills-sync --dry-run [--full]",
"bun scripts/cli.ts codex pr-preflight [--remote] [--push-dry-run --push-dry-run-ref refs/heads/probe/<name>] [--pr-create-dry-run --pr-create-dry-run-head <head>] [--issue N]",
"bun scripts/cli.ts codex pr-preflight [--remote] [--push-dry-run --push-dry-run-ref refs/heads/probe/<name>] [--pr-create-dry-run --pr-create-dry-run-head <head>] [--issue N] [--full|--raw]",
"bun scripts/cli.ts codex judge <taskId> --attempt N [--dry-run] [--include-prompt]",
"bun scripts/cli.ts codex steer <taskId> [prompt|--prompt-file path|--prompt-stdin] [--dry-run] [--no-retry|--retry-attempts N]",
"bun scripts/cli.ts codex interrupt|cancel <taskId>",