From 43c41d302c3411015625520f1da913da1f8a9872 Mon Sep 17 00:00:00 2001 From: John Menke Date: Thu, 17 Sep 2026 14:50:00 -0400 Subject: [PATCH] Fail live-consumer when CURSOR_API_KEY is missing, and cancel overlapping runs. The SDK job skipped when the secret was unset, so the workflow stayed green without running a Cursor agent. That is a skip-PASS. A required job now fails the workflow when the probe reports the key missing. Overlapping runs on the same ref cancel the older matrix (ORCH-04). Proving test: tests/test-orch-03-live-consumer-fail-closed.sh. Removing either half turns it red. Does not call the Cursor API. Co-authored-by: Cursor --- .github/workflows/test-live-consumer.yml | 25 +++++++++ .../test-orch-03-live-consumer-fail-closed.sh | 54 +++++++++++++++++++ 2 files changed, 79 insertions(+) create mode 100755 tests/test-orch-03-live-consumer-fail-closed.sh diff --git a/.github/workflows/test-live-consumer.yml b/.github/workflows/test-live-consumer.yml index 1f767edb..ff6eb493 100644 --- a/.github/workflows/test-live-consumer.yml +++ b/.github/workflows/test-live-consumer.yml @@ -14,6 +14,7 @@ on: - 'engine/**' - 'templates/**' - '.github/workflows/test-live-consumer.yml' + - 'tests/test-orch-03-live-consumer-fail-closed.sh' push: branches: [main] paths: @@ -28,6 +29,11 @@ on: - 'engine/**' - 'templates/**' - '.github/workflows/test-live-consumer.yml' + - 'tests/test-orch-03-live-consumer-fail-closed.sh' + +concurrency: + group: live-consumer-${{ github.ref }} + cancel-in-progress: true jobs: # Deterministic seed/flush consumer (no Cursor API key). @@ -48,6 +54,10 @@ jobs: bash -n tests/test-live-consumer-matrix.sh bash -n tests/live-consumer/*.sh bash -n tests/live-consumer/scenarios/*.sh + bash -n tests/test-orch-03-live-consumer-fail-closed.sh + + - name: ORCH-03 missing key is not a skip-PASS; ORCH-04 concurrency + run: ./tests/test-orch-03-live-consumer-fail-closed.sh - name: Run live consumer shell matrix run: ./tests/test-live-consumer-matrix.sh @@ -68,6 +78,21 @@ jobs: echo "available=false" >> "$GITHUB_OUTPUT" fi + # ORCH-03: a missing key used to skip the SDK job and leave the workflow green. + cursor-sdk-not-skip-pass: + name: Live-consumer SDK is not a skip-PASS + runs-on: ubuntu-latest + needs: cursor-api-key-available + steps: + - name: Fail when CURSOR_API_KEY is missing + env: + AVAILABLE: ${{ needs.cursor-api-key-available.outputs.available }} + run: | + if [[ "${AVAILABLE}" != "true" ]]; then + echo "FAIL: CURSOR_API_KEY is unset. Live-consumer SDK is not a skip-PASS." >&2 + exit 1 + fi + # Real Cursor SDK agents — requires repo secret CURSOR_API_KEY. test-live-consumer-cursor-sdk: runs-on: ubuntu-latest diff --git a/tests/test-orch-03-live-consumer-fail-closed.sh b/tests/test-orch-03-live-consumer-fail-closed.sh new file mode 100755 index 00000000..394fc22f --- /dev/null +++ b/tests/test-orch-03-live-consumer-fail-closed.sh @@ -0,0 +1,54 @@ +#!/usr/bin/env bash +set -euo pipefail + +# ORCH-03 / ORCH-04 proving test. +# ORCH-03: missing CURSOR_API_KEY must fail the workflow, not skip-PASS the SDK job. +# ORCH-04: overlapping live-consumer runs on the same ref must cancel the older one. +# Does not call the Cursor API. +# +# Usage: ./tests/test-orch-03-live-consumer-fail-closed.sh + +SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" +WORKFLOW="$(cd "${SCRIPT_DIR}/.." && pwd)/.github/workflows/test-live-consumer.yml" + +pass=0 +fail=0 +ok() { echo " ok $1"; pass=$((pass + 1)); } +bad() { echo " FAIL $1" >&2; fail=$((fail + 1)); } + +echo "== ORCH-03/04: live-consumer fail-closed + concurrency ==" + +echo "== test_missing_key_is_a_workflow_failure ==" +if grep -Fq 'cursor-sdk-not-skip-pass' "${WORKFLOW}" \ + && grep -Fq 'Live-consumer SDK is not a skip-PASS' "${WORKFLOW}" \ + && grep -Fq 'CURSOR_API_KEY is unset' "${WORKFLOW}"; then + ok "workflow has a required job that fails when the key is missing" +else + bad "workflow dropped the missing-key fail-closed job" +fi + +echo "== test_sdk_job_skip_is_not_the_only_path ==" +# The leftover: SDK job `if: available == true` + no other job → skip-PASS. +# A skip on the SDK job is allowed only if the required job still fails. +if grep -Fq 'if: needs.cursor-api-key-available.outputs.available == '\''true'\''' "${WORKFLOW}" \ + && ! grep -Fq 'cursor-sdk-not-skip-pass' "${WORKFLOW}"; then + bad "SDK job skip is still a skip-PASS (no required missing-key job)" +else + ok "SDK skip cannot hide a missing key" +fi + +echo "== test_concurrency_cancels_the_older_run ==" +if grep -Fq 'group: live-consumer-${{ github.ref }}' "${WORKFLOW}" \ + && grep -Fq 'cancel-in-progress: true' "${WORKFLOW}"; then + ok "workflow concurrency cancels the older live-consumer run" +else + bad "workflow has no live-consumer concurrency group" +fi + +echo +echo "Summary: ${pass} passed, ${fail} failed" +if [[ "${fail}" -gt 0 ]]; then + echo "ORCH-03/04 live-consumer fail-closed gate FAILED." >&2 + exit 1 +fi +echo "ORCH-03/04 live-consumer fail-closed gate passed."