Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
27 commits
Select commit Hold shift + click to select a range
e95fed3
ci(strix): bootstrap orchestrator gateway patch
seonghobae Aug 28, 2026
e98d08e
fix(ci): make Strix bootstrap workflow parseable
seonghobae Aug 28, 2026
f73486e
ci(strix): bootstrap orchestrator gateway patch
seonghobae Aug 28, 2026
2e1db52
ci(strix): rerun orchestrator gateway patch
seonghobae Aug 28, 2026
3af96b4
ci(strix): rerun orchestrator gateway patch
seonghobae Aug 28, 2026
6a2eddb
fix(strix): route default scans through contextual-orchestrator
seonghobae Aug 28, 2026
2a904b1
fix(strix): hash-lock orchestrator sidecar dependencies
seonghobae Aug 28, 2026
198db58
fix(strix): preserve dispatch and private-source routing boundaries
seonghobae Aug 28, 2026
5ff0e96
fix(strix): exclude the requested NVIDIA diagnostic model
seonghobae Aug 28, 2026
5b37c9b
fix(strix): restore exact quick-gate source bytes
seonghobae Aug 28, 2026
48f893b
fix(strix): correct diagnostic fallback warning
seonghobae Aug 28, 2026
6beae6b
fix(strix): mask gateway token before sidecar startup
seonghobae Aug 28, 2026
4c2bdcb
fix(strix): syntax-check every required smoke script
seonghobae Aug 28, 2026
5f1c1da
Merge main into Strix remediation branch
seonghobae Aug 28, 2026
2ef49da
Merge protected main and retain Strix gateway hardening
seonghobae Aug 28, 2026
30540d2
Merge branch 'main' into feat/strix-orchestrator-free-zdr
seonghobae Aug 28, 2026
cc6bb05
test(strix): bind syntax regression to sidecar check
seonghobae Aug 28, 2026
4a694d5
docs(strix): record integrated catalog fix state
seonghobae Aug 28, 2026
4112970
fix(review): keep orchestrator bearer out of step env
seonghobae Aug 28, 2026
dd46e76
fix(strix): qualify gateway child model
seonghobae Aug 28, 2026
0dabda5
fix(ci): restore complete Strix gate fixture
seonghobae Aug 28, 2026
d9ecfaf
test(strix): isolate malformed-sidecar smoke failure
seonghobae Aug 28, 2026
986cfc2
Merge protected main into gateway credential repair
seonghobae Aug 28, 2026
7d24923
fix(review): isolate token loader shell state
seonghobae Aug 28, 2026
dc03010
fix(review): mask gateway tokens only on Actions
seonghobae Aug 28, 2026
7b3c3b2
test(review): isolate non-Actions mask fixture
seonghobae Aug 28, 2026
2c9588e
Merge branch 'main' into feat/strix-orchestrator-free-zdr
seonghobae Aug 28, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion .github/workflows/noema-review.yml
Original file line number Diff line number Diff line change
Expand Up @@ -316,10 +316,11 @@ jobs:
echo "::error::Noema reviewer credential selection succeeded but no token was minted; review cannot submit a verdict."
exit 1
fi
if [ -z "${CONTEXTUAL_ORCHESTRATOR_BASE_URL:-}" ] || [ -z "${CONTEXTUAL_ORCHESTRATOR_TOKEN:-}" ]; then
if [ -z "${CONTEXTUAL_ORCHESTRATOR_BASE_URL:-}" ] || [ -z "${CONTEXTUAL_ORCHESTRATOR_TOKEN_FILE:-}" ]; then
echo "::error::contextual-orchestrator review sidecar must be provisioned before Noema LLM review."
exit 1
fi
source "$GITHUB_WORKSPACE/scripts/ci/load_contextual_orchestrator_token.sh"
export NOEMA_LLM_API_URL="${CONTEXTUAL_ORCHESTRATOR_BASE_URL%/}/v1/chat/completions"
export NOEMA_LLM_MODEL="orchestrator/free"
export NOEMA_LLM_API_KEY="${CONTEXTUAL_ORCHESTRATOR_TOKEN}"
Expand Down
2 changes: 2 additions & 0 deletions .github/workflows/opencode-review-dispatch.yml
Original file line number Diff line number Diff line change
Expand Up @@ -3998,6 +3998,7 @@ jobs:
RUN_ATTEMPT: ${{ github.run_attempt }}
run: |
set -euo pipefail
source "$GITHUB_WORKSPACE/scripts/ci/load_contextual_orchestrator_token.sh"
set +e
timeout --kill-after=30s "${OPENCODE_POOL_STEP_TIMEOUT_SECONDS:-3600}s" \
bash "$GITHUB_WORKSPACE/scripts/ci/run_opencode_review_model_pool.sh"
Expand Down Expand Up @@ -5932,6 +5933,7 @@ jobs:
printf 'Skipping publish-step failed-check OpenCode diagnosis for central review-process self-repair; using collected current-head failed-check logs/SARIF fallback so the publish step stays bounded.\n' >&2
return 1
fi
source "$GITHUB_WORKSPACE/scripts/ci/load_contextual_orchestrator_token.sh"
if [ -z "${CONTEXTUAL_ORCHESTRATOR_TOKEN:-}" ]; then
return 1
fi
Comment thread
seonghobae marked this conversation as resolved.
Expand Down
6 changes: 4 additions & 2 deletions .github/workflows/pr-review-autofix.yml
Original file line number Diff line number Diff line change
Expand Up @@ -376,10 +376,11 @@ jobs:
OPENCODE_AUTOFIX_WORKDIR: ${{ runner.temp }}/opencode-autofix-project
run: |
set -euo pipefail
if [ -z "${CONTEXTUAL_ORCHESTRATOR_BASE_URL:-}" ] || [ -z "${CONTEXTUAL_ORCHESTRATOR_TOKEN:-}" ]; then
if [ -z "${CONTEXTUAL_ORCHESTRATOR_BASE_URL:-}" ] || [ -z "${CONTEXTUAL_ORCHESTRATOR_TOKEN_FILE:-}" ]; then
echo "::error::contextual-orchestrator review sidecar must be provisioned before scheduled OpenCode autofix."
exit 1
fi
source "$GITHUB_WORKSPACE/trusted-autofix-source/scripts/ci/load_contextual_orchestrator_token.sh"
prompt_file="${RUNNER_TEMP}/opencode-autofix-prompt.md"
allowed_paths_zlist="${RUNNER_TEMP}/pr-review-autofix-allowed-paths.zlist"
allowed_paths_context="$(
Expand Down Expand Up @@ -581,10 +582,11 @@ jobs:
echo "::error::Conflict-resolution mutation requires PR_REVIEW_MERGE_TOKEN, OPENCODE_APPROVE_TOKEN, or the exchanged OpenCode app token; github.token remains read-only."
exit 1
fi
if [ -z "${CONTEXTUAL_ORCHESTRATOR_BASE_URL:-}" ] || [ -z "${CONTEXTUAL_ORCHESTRATOR_TOKEN:-}" ]; then
if [ -z "${CONTEXTUAL_ORCHESTRATOR_BASE_URL:-}" ] || [ -z "${CONTEXTUAL_ORCHESTRATOR_TOKEN_FILE:-}" ]; then
echo "::error::contextual-orchestrator review sidecar must be provisioned before scheduled OpenCode conflict resolution."
exit 1
fi
source "$GITHUB_WORKSPACE/trusted-autofix-source/scripts/ci/load_contextual_orchestrator_token.sh"
cd "$TARGET_WORKSPACE"

# Merge the base branch into the detached head. A clean merge stays
Expand Down
4 changes: 4 additions & 0 deletions .github/workflows/strix.yml
Original file line number Diff line number Diff line change
Expand Up @@ -650,6 +650,8 @@ jobs:
env:
PROVIDER_MODE: ${{ steps.gate.outputs.provider_mode }}
run: |
set -euo pipefail
source "$TRUSTED_STRIX_SOURCE/scripts/ci/load_contextual_orchestrator_token.sh"
if [ "$PROVIDER_MODE" != "contextual_orchestrator" ]; then
echo '::error::Strix must use the contextual-orchestrator provider.'
Comment thread
devin-ai-integration[bot] marked this conversation as resolved.
exit 1
Expand All @@ -670,6 +672,8 @@ jobs:
env:
PROVIDER_MODE: ${{ steps.gate.outputs.provider_mode }}
run: |
set -euo pipefail
source "$TRUSTED_STRIX_SOURCE/scripts/ci/load_contextual_orchestrator_token.sh"
if [ "$PROVIDER_MODE" != "contextual_orchestrator" ]; then
echo '::error::Strix must use the contextual-orchestrator provider.'
exit 1
Expand Down
11 changes: 11 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,17 @@ this file. The format follows Keep a Changelog, and versioned releases follow
Semantic Versioning where the repository publishes a release.

## [Unreleased]
- Harden the contextual-orchestrator Strix sidecar by rejecting line-breaking
bearer tokens and masking the token before clone, install, launch, or health
diagnostics can emit it. The raw bearer no longer enters `GITHUB_ENV` (where
a later step header could render it before masking); only a mode-0600 token
file path crosses steps, and each model consumer validates and masks the file
inside its own step. The bounded required-workflow smoke now parses every
governed shell input independently, including the sidecar and token loader.
Strix also qualifies only the loopback child model as
`openai/orchestrator/free`, which satisfies LiteLLM's explicit-provider
contract while preserving `orchestrator/free` at the gateway boundary; a
missing, empty, or non-pinned contextual-orchestrator API base fails closed.
- Restore OpenCode coverage honesty and mermaid surfaces stacked on main after #1360 squash `17052a7c`: `publish_fallback_diff_review` posts a COMMENT product-file review then `request_changes_for_coverage_evidence_failure` sets the status comment to `COVERAGE_BLOCKED` so a coverage miss never looks finished as `Gate result: COMMENT`; mermaid labels crates/packages instead of generic `Changed file (N files)` and does not invent class edges; findings say `Review process` instead of `.github/workflows/opencode-review.yml:1` unless that file is in the diff. Does not change `noema-review.yml` (PM owns `feat/noema-orchestrator-free-zdr`) and is not NIM-2h or GitHub Models.
- Required OpenCode dispatch and Strix now use the vendored
`contextual-orchestrator/orchestrator/free` gateway for model execution and
Expand Down
63 changes: 38 additions & 25 deletions docs/doctoring/contextual-orchestrator-vendored-sidecar.md
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,10 @@ orchestrator's `review_gateway.REVIEW_CREDENTIAL_NAMES`.
- The gateway binds to loopback only; it never leaves the runner. Secrets are
bootstrap transport into the KV and are never read back from environment at
request time.
- The generated bearer is stored in a runner-owned mode-0600 regular file.
`GITHUB_ENV` carries only that path; every Noema, Strix, OpenCode review, and
autofix consumer validates ownership, mode, symlink status, size, and line
structure before reading and masking the bearer inside its own step.
- Noema reviewer identity is unchanged: `NOEMA_REVIEW_TOKEN` / GitHub App /
OIDC. Review mutation is still not `github.token`.

Expand All @@ -77,7 +81,9 @@ training (OpenRouter's own stance). Evidence sources:
- `scripts/ci/contextual_orchestrator_review_launcher.py` — same-process KV
registration + discovery + serve (runs in the vendored runtime only).
- `scripts/ci/contextual_orchestrator_review_sidecar.sh` — pinned-SHA vendoring +
health gate + GITHUB_ENV export.
health gate + private token-file creation and path export.
- `scripts/ci/load_contextual_orchestrator_token.sh` — per-step file validation,
bearer masking, and process-local export for the consuming model command.
- `tests/test_zdr_policy.py`,
`tests/test_contextual_orchestrator_review_policy.py`,
`tests/test_contextual_orchestrator_review_sidecar_contract.py`,
Expand All @@ -91,27 +97,34 @@ training (OpenRouter's own stance). Evidence sources:
The first post-merge Strix execution (`33139957477`) failed before serving: the
pinned orchestrator's `load_agents()` indexes the top-level `agents` field, but
the launcher persisted only the list value. Follow-up PR [#1370](https://github.com/ContextualWisdomLab/.github/pull/1370)
wraps both the launcher output and the standalone policy builder output in the
loader-compatible `{"agents": [...]}` envelope. The regression is covered by
`tests/test_contextual_orchestrator_review_policy.py` and the sidecar contract;
the full local suite passed with `1689 passed, 1 skipped, 16 subtests passed`.

The PR-target Noema check still runs the trusted base copy until this trusted
workflow change is merged, so its reproduction of the old error is retained as
bootstrap evidence rather than treated as a current-head runtime result.

## 2026-08-28 post-#1370 runtime correction

Main push run `33141468804` confirmed that the catalog envelope correction
reached the Strix sidecar, but LiteLLM rejected the child model
`orchestrator/free` because it had no provider prefix. Follow-up commits
`9f58d74` and `5aa0a20` map only the pinned gateway request to
`openai/orchestrator/free`, fail closed when that gateway base is absent or
not loopback, and keep the loopback sidecar receiving `orchestrator/free`.

The same follow-up masks the dynamic sidecar bearer before writing `GITHUB_ENV`
and rejects carriage returns/newlines in an override. This closes the runtime
log exposure observed in the Noema step environment block. Focused contracts
pass (`32 passed`) and the full local suite passes (`1689 passed, 1 skipped`).
The main Strix rerun and an independently authorized Noema model verdict are
still required before claiming end-to-end review completion.
wrapped both the launcher output and the standalone policy builder output in the
loader-compatible `{"agents": [...]}` envelope and merged exact head
`0f40d415b112ca0055f5db5b2f434788b08f01f1` into protected
`main@24ee38b097dbfc1a895e1199ade48cff36431d05`. The regression is covered by
`tests/test_contextual_orchestrator_review_policy.py` and the sidecar contract.

The earlier PR-target Noema failure remains bootstrap evidence because it ran
the pre-fix trusted base copy. Operational acceptance now requires a fresh
protected-main run that starts the corrected sidecar, passes authenticated
health, and reaches the scanner; queued or cancelled jobs are non-passing.

The first corrected-catalog Noema canary reached authenticated health and the
review gate, but its retained job log showed that exporting the raw bearer via
`GITHUB_ENV` exposed it in the next step's rendered environment header before
that step could mask it. The causal repair therefore exports only a private
token-file path and rehydrates the bearer after each consumer step starts. No
credential value is retained in this record.

Protected-main Strix run `33141468804` then proved that the corrected catalog
reached the sidecar, but LiteLLM rejected the unqualified child model
`orchestrator/free` because its provider was not explicit. The repair keeps the
public/gateway model `contextual-orchestrator/orchestrator/free` and maps only
the scanner child to `openai/orchestrator/free` when its API base is exactly
`http://127.0.0.1:18080/v1`. Missing, empty, or other contextual-orchestrator
API bases fail closed. A fresh protected-main run is still required for
operational acceptance.

PR #1373 merged the model qualification into
`main@8f84b661e468de451ba5c076dc938f342bf52d70`, but retained the raw bearer in
`GITHUB_ENV`. PR #1369 supersedes that credential boundary with file-only
cross-step transport; source integration alone remains insufficient acceptance.
52 changes: 23 additions & 29 deletions docs/product-technical-gap-baseline.md
Original file line number Diff line number Diff line change
Expand Up @@ -258,35 +258,29 @@ flowchart LR
- Post-merge Strix run `33139957477` exposed a real sidecar runtime defect:
`contextual_orchestrator.orchestrator.load_agents()` requires an
`{"agents": [...]}` catalog envelope, while the launcher wrote a bare list.
Follow-up #1370 fixes the launcher and the standalone policy catalog writer
in commit `861463c11a7ca8b1f9179073e2a3db9eba5aa5ab`; its current head is
`38e0307c655823a1e474b29aae89f8cfcb1edbc0`. Focused tests and the full local
suite pass (`1689 passed, 1 skipped, 16 subtests passed`).
- #1370 merged on `24ee38b…`; its pre-merge PR-target Noema run
`33140830199` executed the trusted base launcher and reproduced the
pre-fix bare-list error. The post-merge push run below shows that the
catalog-envelope fix reached the Strix sidecar successfully.

## 2026-08-28 post-#1370 Strix runtime recheck

- Main push run `33141468804` reached `Provision contextual-orchestrator Strix
sidecar` successfully, then failed in `Run Strix (quick)`. LiteLLM rejected
the unqualified child model `orchestrator/free` with `LLM Provider NOT
provided`; this is a request-shape defect, not evidence that the sidecar
catalog failed.
- Follow-up commits `9f58d74` and `5aa0a20` qualify only the LiteLLM child
request as `openai/orchestrator/free` when the API base is the pinned
loopback gateway; the gateway still receives `orchestrator/free` and owns
discovery/failover. They also fail closed when that base is absent or not
the pinned loopback, register the dynamic bearer token with `::add-mask::`
before exporting `GITHUB_ENV`, and reject token newlines. Focused contracts
pass (`32 passed`); the full local suite passes (`1689 passed, 1 skipped`).
- A real current-main Noema run on #1369 (`33141494393`) also booted the
sidecar and executed the Noema gate, but correctly skipped the LLM verdict
because the exact head had no primary OpenCode approval. A successful
sidecar/bootstrap step is not counted as a model-review result; post-fix
Strix completion and an independently authorized Noema verdict remain
separate evidence items.
Follow-up #1370 fixes the launcher and the standalone policy catalog writer.
Its exact head `0f40d415b112ca0055f5db5b2f434788b08f01f1` merged as
`24ee38b097dbfc1a895e1199ade48cff36431d05`.
- #1370's earlier PR-target Noema run `33140830199` executed the pre-fix trusted
base launcher and is retained only as bootstrap reproduction evidence. A
fresh protected-main canary must start the corrected sidecar and reach the
scanner before the runtime gap is closed; queued or cancelled jobs do not
satisfy that acceptance boundary.
- Protected-main Strix run `33141468804` crossed the corrected catalog and
sidecar boundary, then LiteLLM rejected the unqualified scanner child model
`orchestrator/free` because the provider was not explicit. The follow-up maps
only that child to `openai/orchestrator/free` when the API base is the pinned
loopback gateway; the public gateway model remains
`contextual-orchestrator/orchestrator/free`, and absent, empty, or non-pinned
bases fail closed. This is reproduction evidence, not operational acceptance.
- #1370 merged with no `APPROVED` review; all recorded Reviews API verdicts are
`COMMENTED`. That governance contradiction is tracked in #1340 and is not
retrospective approval evidence for this runtime correction.
- #1373 merged the model qualification as `8f84b661…` but retained the raw
bearer in `GITHUB_ENV`, so its log-exposure claim is contradicted by source.
#1369 preserves the merged model behavior while moving cross-step credential
transport to a validated mode-0600 file. Fresh protected-main Strix and Noema
evidence is still required after that stronger boundary integrates.

## 2026-08-28 post-#1373 request-envelope recheck

Expand Down
31 changes: 21 additions & 10 deletions scripts/ci/contextual_orchestrator_review_sidecar.sh
100644 → 100755
Comment thread
devin-ai-integration[bot] marked this conversation as resolved.
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
#!/usr/bin/env bash
# Provision the vendored contextual-orchestrator review sidecar on a GitHub
# Actions runner and export CONTEXTUAL_ORCHESTRATOR_BASE_URL / _TOKEN to
# $GITHUB_ENV (when set).
# Actions runner and export the loopback URL plus a private bearer-file path to
# $GITHUB_ENV (when set). The raw bearer must never cross a step boundary in the
# runner environment because GitHub renders that environment before a later
# step can issue its own add-mask command.
#
# The five provider secrets arrive as bootstrap transport only (Actions env) and
# are registered into the process-local KV by the launcher in the SAME process
Expand Down Expand Up @@ -45,16 +47,25 @@ fi
log "provider secrets present: $provider_secret_count of 5"

ORCHESTRATOR_TOKEN="${ORCHESTRATOR_TOKEN:-$(python3 -c 'import secrets; print(secrets.token_urlsafe(32))')}"
if [[ "$ORCHESTRATOR_TOKEN" == *$'\r'* || "$ORCHESTRATOR_TOKEN" == *$'\n'* ]]; then
fail "ORCHESTRATOR_TOKEN must not contain carriage returns or newlines"
fi
if [ -n "${GITHUB_ACTIONS:-}" ]; then
# Register the process-local bearer token before exporting it through
# GITHUB_ENV; later step environment blocks otherwise echo it verbatim.
echo "::add-mask::$ORCHESTRATOR_TOKEN"
case "$ORCHESTRATOR_TOKEN" in
*$'\r'*|*$'\n'*) fail "ORCHESTRATOR_TOKEN must not contain CR or LF" ;;
esac
# Mask the bearer before clone, dependency installation, launcher startup, or
# health diagnostics can emit it. Later masking is too late for earlier logs,
# but workflow commands are safe only on an Actions runner; elsewhere this
# would print the raw bearer to ordinary stdout.
if [ "${GITHUB_ACTIONS:-}" = "true" ]; then
printf '::add-mask::%s\n' "$ORCHESTRATOR_TOKEN"
fi

mkdir -p "$ORCHESTRATOR_WORK"
chmod 700 -- "$ORCHESTRATOR_WORK"
token_file="$ORCHESTRATOR_WORK/bearer.token"
(
umask 077
printf '%s' "$ORCHESTRATOR_TOKEN" > "$token_file"
)
chmod 600 -- "$token_file"
rm -rf "$ORCHESTRATOR_SOURCE"
log "vendoring contextual-orchestrator @ ${ORCHESTRATOR_PIN_SHA}"
git clone --quiet --filter=blob:none --no-checkout "$ORCHESTRATOR_GIT_URL" "$ORCHESTRATOR_SOURCE"
Expand Down Expand Up @@ -144,7 +155,7 @@ log "healthz confirmed after ${i}s (pid $sidecar_pid)"
if [ -n "$ORCHESTRATOR_GITHUB_ENV" ]; then
{
printf 'CONTEXTUAL_ORCHESTRATOR_BASE_URL=http://%s:%s\n' "$ORCHESTRATOR_HOST" "$ORCHESTRATOR_PORT"
printf 'CONTEXTUAL_ORCHESTRATOR_TOKEN=%s\n' "$ORCHESTRATOR_TOKEN"
printf 'CONTEXTUAL_ORCHESTRATOR_TOKEN_FILE=%s\n' "$token_file"
printf 'CONTEXTUAL_ORCHESTRATOR_EVIDENCE=%s\n' "$policy_report"
} >> "$ORCHESTRATOR_GITHUB_ENV"
log "exported gateway env to $ORCHESTRATOR_GITHUB_ENV"
Expand Down
47 changes: 47 additions & 0 deletions scripts/ci/load_contextual_orchestrator_token.sh
Comment thread
seonghobae marked this conversation as resolved.
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
#!/usr/bin/env bash
# Source inside a model-consuming GitHub Actions step. The provisioner exports
# only this file path across steps so the raw bearer cannot appear in a later
# step's rendered environment header before masking takes effect.

_contextual_orchestrator_token_fail() {
printf '::error::%s\n' "$*" >&2
return 1
}

_contextual_orchestrator_load_token() {
local token_file token_size

token_file="${CONTEXTUAL_ORCHESTRATOR_TOKEN_FILE:-}"
if [ -z "$token_file" ]; then
_contextual_orchestrator_token_fail "CONTEXTUAL_ORCHESTRATOR_TOKEN_FILE is required; the review sidecar was not provisioned." || return 1
fi
if [ ! -f "$token_file" ] || [ -L "$token_file" ]; then
_contextual_orchestrator_token_fail "CONTEXTUAL_ORCHESTRATOR_TOKEN_FILE must name a regular, non-symlink file." || return 1
fi
if [ "$(stat -c %u -- "$token_file")" != "$(id -u)" ]; then
_contextual_orchestrator_token_fail "CONTEXTUAL_ORCHESTRATOR_TOKEN_FILE must be owned by the current runner user." || return 1
fi
if [ "$(stat -c %a -- "$token_file")" != "600" ]; then
_contextual_orchestrator_token_fail "CONTEXTUAL_ORCHESTRATOR_TOKEN_FILE must have mode 600." || return 1
fi
token_size="$(wc -c < "$token_file")"
if [ "$token_size" -lt 1 ] || [ "$token_size" -gt 4096 ]; then
_contextual_orchestrator_token_fail "CONTEXTUAL_ORCHESTRATOR_TOKEN must contain between 1 and 4096 bytes." || return 1
fi
if [ "$(wc -l < "$token_file")" -ne 0 ] || grep -q $'\r' -- "$token_file"; then
_contextual_orchestrator_token_fail "CONTEXTUAL_ORCHESTRATOR_TOKEN must not contain CR or LF." || return 1
fi

CONTEXTUAL_ORCHESTRATOR_TOKEN="$(cat -- "$token_file")"
if [ "${GITHUB_ACTIONS:-}" = "true" ]; then
printf '::add-mask::%s\n' "$CONTEXTUAL_ORCHESTRATOR_TOKEN"
fi
Comment on lines +36 to +38

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

📝 Info: Job-wide mask already covers the fresh bearer

The loader's per-step re-mask is defensive: the sidecar generates a fresh per-job token and registers ::add-mask:: at provisioning, and masks persist across the job's later steps. Even where the loader's mask output might be captured rather than logged, the token stays masked from that initial registration. The GITHUB_ACTIONS guard narrowing to exactly true holds on hosted runners.

Devin Review

Was this helpful? React with 👍 or 👎 to provide feedback.

export CONTEXTUAL_ORCHESTRATOR_TOKEN
}

_contextual_orchestrator_load_token || {
_contextual_orchestrator_status=$?
unset -f _contextual_orchestrator_load_token _contextual_orchestrator_token_fail
return "$_contextual_orchestrator_status"
}
unset -f _contextual_orchestrator_load_token _contextual_orchestrator_token_fail
Comment on lines +42 to +47

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

📝 Info: Loader fail-closed semantics under set -e

The worker runs as _contextual_orchestrator_load_token || { ... }, which disables set -e inside the function, so bare stat/wc/cat cannot abort mid-validation. Failures propagate through explicit || return N, and the top-level return makes source non-zero, so consuming steps fail closed. Subtle but correct.

Devin Review

Was this helpful? React with 👍 or 👎 to provide feedback.

Loading
Loading