fix: pass version inputs via env to prevent expression injection - #225
Merged
Merged
Conversation
The composite `run:` step spliced `${{ inputs.version }}`,
`${{ inputs.yamllint_version }}` and `${{ inputs.yamale_version }}`
directly into a bash command line. GitHub substitutes `${{ }}`
textually before bash parses the script, so a caller that derives any of
those values from untrusted data (a PR title, branch name or issue body)
can inject arbitrary shell commands into this action.
Pass each input through step-level `env:` instead and reference the
quoted shell variables, so the value stays a single argv element that
bash never re-evaluates. Also quote `$GITHUB_ACTION_PATH` so the `cd`
does not word-split on a path containing spaces.
The env vars are deliberately not named `CT_*`, since chart-testing
reads `CT_*` from the environment as its own viper configuration.
`ct.sh` needed no change: it already quotes `"${2#v}"` and stores
argument values verbatim without re-evaluating them.
Verified: reproduced command execution against the old form
(`--version '3.14.0; touch /tmp/PWNED'` created the marker file) and
confirmed the `env:` form passes the same hostile value through inert.
actionlint clean.
Signed-off-by: Carlos Panato <ctadeu@gmail.com>
cpanato
force-pushed
the
harden-action-yml-injection
branch
from
September 17, 2026 08:29
854739e to
46209b7
Compare
davidkarlsen
approved these changes
Sep 19, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
The composite
run:step spliced${{ inputs.version }},${{ inputs.yamllint_version }}and${{ inputs.yamale_version }}directly into a bash command line. GitHub substitutes${{ }}textually before bash parses the script, so a caller that derives any of those values from untrusted data (a PR title, branch name or issue body) can inject arbitrary shell commands into this action.Pass each input through step-level
env:instead and reference the quoted shell variables, so the value stays a single argv element that bash never re-evaluates. Also quote$GITHUB_ACTION_PATHso thecddoes not word-split on a path containing spaces.The env vars are deliberately not named
CT_*, since chart-testing readsCT_*from the environment as its own viper configuration.ct.shneeded no change: it already quotes"${2#v}"and stores argument values verbatim without re-evaluating them.Verified: reproduced command execution against the old form (
--version '3.14.0; touch /tmp/PWNED'created the marker file) and confirmed theenv:form passes the same hostile value through inert. actionlint clean.