Files
orca/config/scripts/git-pull-request-diff-base.mjs
T
Jinwoo-H 31f76e445f ci: fail a PR that rewrites an existing test's expected outcome
#19542 deleted the orchestration legacy-Run write fallbacks and broke
`orca orchestration send` between two plain terminals. The e2e test that
already caught it went red on main, and #19684 then renamed that test and
asserted the new error as a test-only PR, hours before users reported the
break. No gate had an opinion, because "the test now expects the opposite"
is not a lint finding, a type error, or a red suite.

The gate reads the PR's own diff for three shapes inside tests/e2e/** and
src/main/runtime/rpc/methods/orchestration/**: a renamed test title, a
success path replaced by an error expectation, and a populated expectation
replaced by an empty one. Any of them means the PR is changing what the
product is expected to do, so the body has to carry a "## User-visible
change" section with Before:/After: lines. Reverse flips (an error
expectation replaced by a value one) are not flagged, so a fix restoring
behaviour pays nothing.

It runs as a step in static_analysis rather than a job of its own: that job
is already in verify.needs, already runs on every non-docs PR, and already
fetches the full history the merge-base diff needs. The body arrives via
the PR_BODY env var, never interpolated into the shell.

Base resolution moves out of check-changed-code-quality.mjs into the shared
git-pull-request-diff-base.mjs so both changed-code gates resolve the base
the same way instead of keeping two copies.
2026-09-09 19:09:37 -04:00

47 lines
1.3 KiB
JavaScript

import { execFileSync, spawnSync } from 'node:child_process'
import process from 'node:process'
export function selectPullRequestDiffBase(requestedBase, headParents, eventName) {
if (eventName === 'pull_request' && headParents.length >= 2) {
return headParents[0]
}
return requestedBase
}
export function resolvePullRequestDiffBase(
root,
requestedBase,
eventName = process.env.GITHUB_EVENT_NAME
) {
const [, ...headParents] = execFileSync('git', ['rev-list', '--parents', '-n', '1', 'HEAD'], {
cwd: root,
encoding: 'utf8'
})
.trim()
.split(/\s+/)
return selectPullRequestDiffBase(requestedBase, headParents, eventName)
}
// Shared by every changed-code gate: the first candidate that names a real commit.
// ORCA_CODE_QUALITY_BASE stays supported so one override still steers all of them.
export function resolveExistingDiffBase(root, requestedBase) {
for (const candidate of [
requestedBase,
process.env.ORCA_CODE_QUALITY_BASE,
'origin/main',
'main'
]) {
if (!candidate) {
continue
}
const result = spawnSync('git', ['rev-parse', '--verify', `${candidate}^{commit}`], {
cwd: root,
stdio: 'ignore'
})
if (result.status === 0) {
return candidate
}
}
throw new Error('Pass the pull request base SHA or make origin/main available locally.')
}