Files
codebase-memory-mcp/tests/test_harness_selection.sh
T
Martin Vogel 776bb119ac ci(test-impact): team artifact producer, PR shadow and the PR-CI narrowing switch
Producer. test-impact-artifact.yml publishes, on every push to main, the
commit's team artifact bundle: its frozen graph, built incrementally from the
previous bundle, and its per-test coverage map, re-run only for the suites
the push selects (scripts/ci/test-impact-publish.sh). A weekly run rebuilds
both from scratch and fails when the incremental graph's topology differs
from the full one. Bundles are Actions artifacts kept 30 days, never
committed.

Shadow. The report-only test-impact-shadow job also builds the checkout and
runs `test-impact select` against the base side of the PR merge commit
(scripts/ci/test-impact-select.sh). A bundle is used only when it comes from
a successful main-branch producer run for exactly that commit
(scripts/ci/test-impact-bundle.sh). The job stays continue-on-error and
outside ci-ok.

Narrowing switch, PR CI only. While the repository variable
TEST_IMPACT_MODE is `gate`, a select-tests job turns the engine's answer into
the tests the test-unix and test-windows legs run. Unset, nothing changes.
It fails open by construction:
- scripts/test-impact/selection.py is the only place an answer becomes a
  runner filter. Only a well-formed selected lane whose filter matches its
  own suite list narrows; run-all answers, a lane that selects nothing,
  unknown schemas or tokens, and any crash run everything.
- `test` passes a selection only from a successful, narrowed select-tests
  run; ci-ok does not need select-tests. A broken selection costs minutes,
  never coverage.
- scripts/run-tests-parallel.sh launches only the selected suites and keeps
  every guard on the selected list. A selected suite the build does not
  register fails the run, unless the engine saw its registration as
  conditional; then it is dropped with a notice, exactly as a full run of
  that build never runs it. Each runner judges its own tokens, so a selected
  test that does not exist fails its suite.
- The shard manifest records the selection's digest, and
  verify-shard-union.sh requires every shard of a leg to agree on it.
- Dry runs and releases never pass a selection (lane-wiring contract).

Also fixed on the way:
- publish crashed on any run-all push: a run-all lane carries
  "suites": null.
- the git-facts hostile-diff probe re-ran the runner with the parent's
  CBM_TEST_ONLY_FILE still set; under a narrowed run naming its suite it
  re-ran the spawning test, which spawned again. The child now clears it
  (a new test fails without that).
- the select summary crashed on the same null suites.

Contracts: tests/test_test_impact_selection.sh (Step 0z8),
tests/test_harness_selection.sh (Step 2c, the real runner through the real
harness), and new cases in the lane-gate and lane-wiring contracts.

Signed-off-by: Martin Vogel <martin.vogel.tech@gmail.com>
2026-10-05 18:52:31 +02:00

104 lines
4.7 KiB
Bash

#!/usr/bin/env bash
# PR CI's test selection in the parallel harness (scripts/run-tests-parallel.sh,
# CBM_TEST_SELECTION_FILE / CBM_TEST_SELECTION_OPTIONAL), driven over the
# runner just built — the same binary and scheduler every leg runs:
# 1. only the selected suites are launched, each runner applies the tokens
# (a narrowed suite deselects its other tests), and the shard manifest
# records the selected list and the selection's digest;
# 2. a selected suite this build does not register FAILS the run, unless the
# selection marks it conditional, when it is dropped with a notice;
# 3. a malformed selection and a selected test the build does not have FAIL.
# A selection that quietly ran less than it named would report green for work
# that never ran.
set -euo pipefail
ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"
RUNNER="${CBM_TEST_RUNNER:-${ROOT}/build/c/test-runner}"
if [[ ! -x "${RUNNER}" && -x "${RUNNER}.exe" ]]; then
RUNNER="${RUNNER}.exe"
fi
if [[ ! -x "${RUNNER}" ]]; then
echo "missing test runner: ${RUNNER}" >&2
exit 2
fi
# Relative paths, as the real run uses them: the native Windows runner reads
# the selection file the harness writes under its log directory.
cd "${ROOT}"
RUNNER_REL="${RUNNER#"${ROOT}"/}"
LOGS="$(dirname "${RUNNER_REL}")/test-logs-selection"
# Anything inherited from the caller would decide the cases below.
unset CBM_TEST_ONLY CBM_TEST_ONLY_FILE CBM_TEST_SELECTION_FILE CBM_TEST_SELECTION_OPTIONAL
unset CBM_TEST_SHARD CBM_TEST_LEG
NAMED_SUITE=dyn_array
OTHER_SUITE=str_intern
OTHER_TEST="$(awk -F'[()]' '/^[[:space:]]*RUN_TEST\(/ { print $2; exit }' "tests/test_${OTHER_SUITE}.c")"
OTHER_TOTAL="$(awk '/^[[:space:]]*RUN_TEST\(/ { n++ } END { print n + 0 }' "tests/test_${OTHER_SUITE}.c")"
if [[ -z "${OTHER_TEST}" || "${OTHER_TOTAL}" -lt 2 ]]; then
echo "fixture suite changed shape: ${OTHER_SUITE}=${OTHER_TOTAL}" >&2
exit 2
fi
tmpdir="$(mktemp -d "${TMPDIR:-/tmp}/cbm-selection.XXXXXX")"
trap 'rm -rf "${tmpdir}" "${LOGS}"' EXIT
FAILURES=0
fail() {
echo "FAIL: $*" >&2
FAILURES=$((FAILURES + 1))
}
# harness <case> <selection lines> [optional suites] -> RC, OUT
harness() {
printf '%b' "$2" > "${tmpdir}/$1.sel"
local optional=()
if [[ -n "${3:-}" ]]; then
printf '%b' "$3" > "${tmpdir}/$1.opt"
optional=(CBM_TEST_SELECTION_OPTIONAL="${tmpdir}/$1.opt")
fi
RC=0
OUT="$(env CBM_TEST_LOG_DIR="${LOGS}" CBM_TEST_SELECTION_FILE="${tmpdir}/$1.sel" \
${optional[@]+"${optional[@]}"} \
bash scripts/run-tests-parallel.sh "${RUNNER_REL}" 2 2>&1 | tr -d '\r')" || RC=$?
}
ran_suites() {
awk '{ print $1 }' "${LOGS}/results.txt" | sort | tr '\n' ' '
}
# 1. Narrowed: one whole suite, one suite by a single test.
harness narrowed "${NAMED_SUITE}\n${OTHER_SUITE}:${OTHER_TEST}\n"
[[ "${RC}" -eq 0 ]] || fail "a valid selection failed (exit ${RC}): ${OUT}"
[[ "$(ran_suites)" == "${NAMED_SUITE} ${OTHER_SUITE} " ]] ||
fail "launched suites: $(ran_suites)"
grep -q "deselected" "${LOGS}/${OTHER_SUITE}.log" ||
fail "${OTHER_SUITE} ran unnarrowed: $(tail -3 "${LOGS}/${OTHER_SUITE}.log")"
grep -qE '^ *1 passed' "${LOGS}/${OTHER_SUITE}.log" ||
fail "${OTHER_SUITE} did not run exactly its selected test"
[[ "$(sed -n '/^--- slice ---$/,$p' "${LOGS}/shard-manifest.txt" | tail -n +2 | sort | tr '\n' ' ')" == \
"${NAMED_SUITE} ${OTHER_SUITE} " ]] || fail "the manifest slice is not the selected list"
grep -qE '^selection_sha256=[0-9a-f]{64}$' "${LOGS}/shard-manifest.txt" ||
fail "the manifest does not record the selection digest"
# 2. A selected suite this build does not register.
harness unknown_suite "${NAMED_SUITE}\nno_such_suite\n"
[[ "${RC}" -ne 0 && "${OUT}" == *"does not register"*"no_such_suite"* ]] ||
fail "an unregistered selected suite did not fail the run (exit ${RC})"
harness optional_suite "${NAMED_SUITE}\nno_such_suite\n" "no_such_suite\n"
[[ "${RC}" -eq 0 && "${OUT}" == *"not in this build, not run: no_such_suite"* ]] ||
fail "a conditional suite absent from this build was not dropped (exit ${RC}): ${OUT}"
[[ "$(ran_suites)" == "${NAMED_SUITE} " ]] || fail "optional case launched: $(ran_suites)"
# 3. Malformed selections and unknown tests fail.
harness malformed "${NAMED_SUITE} extra\n"
[[ "${RC}" -ne 0 ]] || fail "a malformed selection was accepted"
harness empty ""
[[ "${RC}" -ne 0 ]] || fail "an empty selection was accepted"
harness unknown_test "${OTHER_SUITE}:no_such_test_in_this_build\n"
[[ "${RC}" -ne 0 ]] || fail "a selected test the build does not have did not fail the run"
if [[ "${FAILURES}" -ne 0 ]]; then
echo "test selection harness: ${FAILURES} case(s) failed" >&2
exit 1
fi
echo "test selection harness: all cases passed"