Unvalidated Workflow Input
Description
Workflows with workflow_dispatch inputs that are optional or used in shell commands without validation create security risks: optional inputs may be used without proper validation, inputs can be used in shell commands or file operations enabling injection attacks, and missing validation can lead to path traversal or code injection. Unvalidated inputs are a common vector for command injection and other security vulnerabilities. 1
Vulnerable Instance
- Workflow has
workflow_dispatchinputs that are optional or used without validation. - Inputs are used in shell commands or file operations.
- Attacker can inject malicious code through inputs.
name: Deploy
on:
workflow_dispatch:
inputs:
environment:
type: string
required: false # Optional, unvalidated
jobs:
deploy:
runs-on: ubuntu-latest
steps:
- name: Deploy
run: |
deploy.sh ${{ inputs.environment }} # Dangerous - unvalidatedMitigation Strategies
Make inputs required when necessary
Setrequired: truefor inputs that must be provided. This ensures inputs are always present and can be validated.Validate inputs before use
Validate inputs against allowlists, check for required values, and reject inputs that don’t match expected patterns.Use input types with validation
Usechoicetype when possible to restrict inputs to specific options. This prevents arbitrary input values.Sanitize inputs used in shell commands
Sanitize all inputs before using them in shell commands. Escape special characters and use parameterized commands.Review all workflow_dispatch inputs
Audit all workflows forworkflow_dispatchinputs. Ensure all inputs are validated before use.Use environment variables
Pass inputs through environment variables instead of direct interpolation in commands. This reduces injection risk.
Secure Version
name: Deploy
on:
workflow_dispatch:
inputs:
environment:
- type: string
- required: false # Optional, unvalidated
+ type: choice # Restricted choices
+ options: [production, staging]
+ required: true
jobs:
deploy:
runs-on: ubuntu-latest
steps:
+ - name: Validate input
+ run: |
+ if [[ "${{ inputs.environment }}" != "production" && "${{ inputs.environment }}" != "staging" ]]; then
+ echo "Invalid environment"
+ exit 1
+ fi
- name: Deploy
+ env:
+ ENV: ${{ inputs.environment }}
run: |
- deploy.sh ${{ inputs.environment }} # Dangerous - unvalidated
+ deploy.sh "$ENV" # Validated, quoted
Impact
| Dimension | Severity | Notes |
|---|---|---|
| Likelihood | Unvalidated workflow inputs are common, especially in deployment workflows, and create high risk when used in commands. | |
| Risk | Unvalidated inputs can enable command injection, path traversal, or other attacks that compromise the workflow and its permissions. | |
| Blast radius | Compromised workflows can affect all systems the workflow can access, including repositories, secrets, and deployment targets. |
References
- GitHub Docs, “Security hardening for GitHub Actions,” https://docs.github.com/en/actions/security-guides/security-hardening-for-github-actions 1
GitHub Docs, “Security hardening for GitHub Actions,” https://docs.github.com/en/actions/security-guides/security-hardening-for-github-actions ↩︎ ↩︎