flawopen.com/GitHub-Actions-Sicherheit/Workflow-Script-Injection
Wie entsteht Script-Injection in GitHub Actions, und wie lässt sie sich verhindern?
Ein Workflow kann Daten in Shell-Syntax verwandeln, wenn er einen Issue-Titel oder ein Pull-Request-Feld vor dem Bash-Start in das Script einsetzt. Wie ein Drucker, der einen Namen für einen Befehl hält. Übergeben Sie den Wert per Umgebungsvariable und quotieren Sie die Expansion, wenn Sie ihn als Daten verwenden. Bash erhält ihn so getrennt vom Script. Die Auswirkung hängt weiterhin von Token, Secrets, Runner und Ereignis ab.
${{ ... }} vor dem Shell-Start aus. In run: kann Eingabe so in den Script-Quelltext gelangen.env: übergibt Werte als Prozessdaten. Shell-Expansion quotieren; eval und dynamische Scripts vermeiden.Ursache: Daten gelangen vor der Shell-Analyse ins Script
GitHub expandiert Ausdrücke, bevor die Shell eines run-Schritts startet. Wird ein nicht vertrauenswürdiger Titel direkt eingesetzt, können seine Zeichen das Shell-Programm verändern. Ein Wert aus env: bleibt vom Scripttext getrennt; quotiert bleibt er bei normalen Befehlen ein Argument. Das macht eine spätere Verwendung mit eval, einem anderen Interpreter oder einem Argumente als Code deutenden Tool nicht sicher. GitHub stuft Ereignisfelder als potenziell angreiferkontrollierte Eingaben ein.
# UNSICHER: Ereignisdaten werden Teil des erzeugten Shell-Scripts
name: Issue Triage
on:
issues:
types: [opened]
permissions:
contents: read
jobs:
triage:
runs-on: ubuntu-latest
steps:
- name: Print issue title
run: |
printf 'Title: %s\n' "${{ github.event.issue.title }}"
# Sicherer: Ereigniswert über die Umgebung übergeben
name: Issue Triage
on:
issues:
types: [opened]
permissions:
contents: read
jobs:
triage:
runs-on: ubuntu-latest
steps:
- name: Print issue title
env:
ISSUE_TITLE: ${{ github.event.issue.title }}
run: |
printf 'Title: %s\n' "$ISSUE_TITLE"
Angriffspfad im Überblick
Benutzer kontrolliert ein Ereignisfeld
Etwa ein öffentlicher Issue- oder Pull-Request-Titel oder ein Branch-Name wird zur Workflow-Eingabe.
Workflow setzt es in Shell-Quelltext ein
Ein Ausdruck ${{ github.event... }} in run: wird ausgewertet, bevor Bash das Script parst.
Shell interpretiert das geänderte Programm
Ändert der Wert die Syntax, laufen Befehle mit der Prozessidentität des Jobs. Als quotiertes Argument bleibt der Wert dagegen Daten.
Job-Rechte bestimmen die Auswirkung
Ein kompromittierter Job erreicht nur Ressourcen dieses Laufs: effektive GITHUB_TOKEN-Rechte, Secrets und Runner. Issue-Ereignisse und pull_request_target sorgfältig prüfen.
Härtungs-Checkliste
- ✓Nicht vertrauenswürdige
github.event-Werte nie direkt inrun:interpolieren. Perenv:übergeben und Expansionen wie"$ISSUE_TITLE"quotieren. - ✓Solche Werte aus
eval, generierten Scripts, Shell-Befehlszeichenketten und Tools fernhalten, die Argumente als Code oder Optionen deuten. - ✓Restriktive
permissions:setzen; Schreibrechte nur dem Job geben, der sie benötigt. - ✓
pull_request_targetundworkflow_runals privilegierte Grenzen behandeln. Dort keinen nicht vertrauenswürdigen PR-Code oder Artefakte auschecken, bauen oder ausführen. - ✓Keine nicht vertrauenswürdigen mehrzeiligen Daten in
GITHUB_ENVoderGITHUB_PATHschreiben.GITHUB_*undRUNNER_*sind geschützt; andere Werte können Folgeschritte beeinflussen. - ✓Drittanbieter-Actions auf geprüfte vollständige SHAs festlegen, isolierte kurzlebige Runner verwenden und CodeQL für Actions-Workflows aktivieren.
Primärquellen
- GitHub Docs — Script-Injections
- GitHub Docs — Sichere Verwendung
- GitHub Docs — pull_request_target sicher verwenden
- GitHub Docs — Workflow-Befehle und GITHUB_ENV
- GitHub Docs — GITHUB_TOKEN-Berechtigungen