Summary
gh aw compile (v0.80.6) fails with a template-injection error on its own generated code for workflows that use a workflow_dispatch input inside safe-outputs.target-repo (multi-repo checkout). The compiler inlines the raw ${{ github.event.inputs.* }} expression into a shell command in the generated "Configure Git credentials" step, then the (correct) injection scanner rejects it. This is a regression: v0.79.6 generated the safe, env-var form for the same source.
Net effect: multi-repo workers that compiled cleanly on v0.79.6 can no longer be compiled on v0.80.6.
Environment
- gh-aw: v0.80.6 (pre-release)
- Last known-good: v0.79.6 (and v0.79.8)
- Engine: copilot
Repro
A workflow whose frontmatter wires a workflow_dispatch input into safe-outputs target-repo, e.g.:
on:
workflow_dispatch:
inputs:
target_repo:
required: true
safe-outputs:
create_pull_request:
target-repo: "github/${{ github.event.inputs.target_repo }}"
push_to_pull_request_branch:
target-repo: "github/${{ github.event.inputs.target_repo }}"
Run gh aw compile.
Actual behaviour (v0.80.6)
Compilation fails:
error: template injection vulnerabilities detected in compiled workflow
github.event context (1 occurrence(s)):
- ${{ github.event.inputs.target_repo }}
in: git -C "./target-repo" remote set-url origin "https://x-access-token:${GIT_TOKEN}@${GIT_SERVER_UR...
The offending generated step (Configure Git credentials) in the .lock.yml:
env:
GIT_TOKEN: ${{ steps.safe-outputs-app-token.outputs.token }}
run: |
bash "${RUNNER_TEMP}/gh-aw/actions/configure_git_credentials.sh"
GIT_SERVER_URL_STRIPPED="${GITHUB_SERVER_URL#https://}"
# Re-authenticate git for github/${{ github.event.inputs.target_repo }}
git -C "./target-repo" remote set-url origin "https://x-access-token:${GIT_TOKEN}@${GIT_SERVER_URL_STRIPPED}/github/${{ github.event.inputs.target_repo }}.git"
The expression is interpolated directly into the run: shell - the exact pattern the scanner flags (and rightly so). The compiler also writes the result to <workflow>.invalid.yml instead of .lock.yml.
Expected behaviour (matches v0.79.6)
The generated step should pass the target repo through a sanitized env var, as v0.79.6 did:
env:
REPO_NAME: github/${{ github.event.inputs.target_repo }}
GIT_TOKEN: ${{ steps.safe-outputs-app-token.outputs.token }}
run: |
...
git -C "./target-repo" remote set-url origin "https://x-access-token:${GIT_TOKEN}@${SERVER_URL_STRIPPED}/${REPO_NAME}.git"
i.e. no ${{ ... }} expression inside the run: body.
Impact
- Blocks upgrading multi-repo /
target-repo workflows from v0.79.x to v0.80.6.
- v0.80.6 is the only release carrying the gh-aw-firewall v0.27.7 default bump (AIC accounting fixes), so consumers can't pick up that firewall fix without also hitting this regression. v0.80.0-v0.80.4 ship firewall v0.27.4.
Suspected cause
Likely introduced alongside the multi-repo "Configure Git credentials" codegen for target-repo checkouts. The single-repo path still emits the safe ${REPO_NAME} form; the per-target-repo remote set-url line inlines the raw expression instead.
Summary
gh aw compile(v0.80.6) fails with a template-injection error on its own generated code for workflows that use aworkflow_dispatchinput insidesafe-outputs.target-repo(multi-repo checkout). The compiler inlines the raw${{ github.event.inputs.* }}expression into a shell command in the generated "Configure Git credentials" step, then the (correct) injection scanner rejects it. This is a regression: v0.79.6 generated the safe, env-var form for the same source.Net effect: multi-repo workers that compiled cleanly on v0.79.6 can no longer be compiled on v0.80.6.
Environment
Repro
A workflow whose frontmatter wires a
workflow_dispatchinput intosafe-outputstarget-repo, e.g.:Run
gh aw compile.Actual behaviour (v0.80.6)
Compilation fails:
The offending generated step (
Configure Git credentials) in the.lock.yml:The expression is interpolated directly into the
run:shell - the exact pattern the scanner flags (and rightly so). The compiler also writes the result to<workflow>.invalid.ymlinstead of.lock.yml.Expected behaviour (matches v0.79.6)
The generated step should pass the target repo through a sanitized env var, as v0.79.6 did:
i.e. no
${{ ... }}expression inside therun:body.Impact
target-repoworkflows from v0.79.x to v0.80.6.Suspected cause
Likely introduced alongside the multi-repo "Configure Git credentials" codegen for
target-repocheckouts. The single-repo path still emits the safe${REPO_NAME}form; the per-target-reporemote set-urlline inlines the raw expression instead.