The short version: GhostAction is a GitHub Actions supply-chain campaign in which attackers use a hijacked maintainer account, most likely accessed through a leaked personal access token, to push a workflow file disguised as a security audit directly to a repository's default branch. The workflow runs under the victim's own GitHub identity on the next push, reads whichever CI/CD secrets the repo already references, and in its newer variants also greps the working tree and full git history for cloud and AI provider keys. Everything it finds is POSTed in cleartext, over plain HTTP, to a hardcoded attacker IP. GitGuardian tracked one wave of this campaign to 772 public repositories across 373 GitHub users and organizations between August 31 and September 30, 2026, and a follow-on burst in early October pushed the same payload into tens of thousands more.
What GitGuardian found
GitGuardian first named this campaign GhostAction in September 2025, after discovering that a massive supply chain attack affecting 327 GitHub users across 817 repositories had exfiltrated thousands of CI/CD secrets. The researchers were candid about the gap in their findings: in a later update to that post they wrote that the initial attack vector remains unknown, even as the malicious infrastructure kept resurfacing.
A year later, the campaign came back. GitGuardian's follow-up research found that between Aug. 31 and Sept. 30, 2026, the malicious workflow was pushed to 772 public repositories belonging to 373 GitHub users and organizations, targeting 2,577 secrets using the same injected workflow technique documented the year before. As in the original wave, every commit was made with the victim's own identity, using what appear to be stolen credentials.
The story didn't stop there. Within days of that report, Socket identified a fresh and larger burst of the same campaign. By October 9, 2026, Socket said it had identified more than 500 GitHub accounts that committed the malicious workflow to tens of thousands of repositories since October 7, 2026. Two of the compromised accounts belonged to maintainers of well-known open-source projects: an initially analyzed October 8 burst affected 346 repositories through compromised maintainer accounts henrywoo and kitao, the authors behind Uber's athenadriver library and the 18,000-star pyxel game engine, respectively.
How the attack actually works, step by step
Strip away the branding and GhostAction is a small number of mechanical steps repeated at scale. Security researchers who reverse-engineered the payload describe a consistent lifecycle.
1 · Account compromise
Researchers at StepSecurity assess that the attacker obtains a maintainer's GitHub credential, most plausibly a leaked personal access token from infostealer logs or credential dumps that circulate among multiple actors. GitGuardian has not confirmed the exact entry point for either wave, only that the commits were authenticated as the real maintainer.
2 · Reconnaissance
Before writing anything, the attacker reads the repository's existing workflow files. The repository's workflow files are scanned for ${{ secrets.NAME }} references, and the exact secret names found are templated into the payload before it is committed — so the malicious file only ever asks for secrets that are known to exist.
3 · Injection
A workflow disguised as a security enhancement is committed directly to the default branch under the victim's own identity. The next push, including the injection push itself, triggers it. Because the commit comes from a trusted maintainer account, it sails past the kind of review a stranger's pull request would get.
4 · Exfiltration
On execution, the workflow waits for a normal repository push, reads selected GitHub Actions secrets, and sends them to attacker-controlled infrastructure through a curl POST request. In the 2026 wave, the latest payload sends data over plain HTTP to 193.32.204.199 — no TLS, no obfuscation.
From "steal the named secret" to "steal anything that looks like a key"
The earliest GhostAction payloads only took what a repository's own workflows already referenced by name — a PyPI token, a DockerHub password. The October 2026 variant goes further. Reverse-engineering by Socket and GBHackers found the payload now runs a regex sweep against both the checked-out files and the complete commit history. Thirteen credential patterns cover AWS access identifiers, secret keys and session tokens; Anthropic, OpenAI and OpenRouter API keys; GitHub and GitLab tokens; and Google, Slack and SendGrid credentials — which is how a campaign that started as a GitHub token thief became a story about stolen AI provider keys.
It also stopped trusting the current state of the repository. StepSecurity found that the payload runs git log -p --all to sweep every commit on every branch, not just the current working tree — meaning a key you committed and deleted two years ago is still fair game, with the search capped at 200,000 lines of history per Socket's analysis.
The adjacent-key trick, and why partial exposure is never safe
The most instructive piece of the October payload is how it handles AWS credentials specifically. An AWS access key ID (the AKIA... string) is not secret by itself — it identifies an account but can't authenticate anything alone. The attacker clearly knows this. Rather than just collecting the key ID, the workflow captures two surrounding lines of context around every AKIA/ASIA match, wrapping the result in markers researchers labeled AKIA_CTX_START and AKIA_CTX_END.
That context matters because of where these key IDs usually live. As Socket's analysis put it, the corresponding 40-character secret access key is what an attacker needs, and in practice it sits one or two lines away in an .env file, an AWS credentials file, a Terraform variables file, or a CI configuration block. Grab the two lines around the identifier and you often reconstruct a complete, usable key pair — even though no single regex match on its own would have given the attacker anything dangerous.
The KnoxCall angle: a poisoned workflow can't exfiltrate what the runner never holds
GhostAction doesn't rely on a sophisticated exploit. It relies on something more mundane: once an attacker can push a workflow file, that workflow inherits read access to every secret GitHub Actions is configured to expose to it, and a curl command is enough to send them anywhere. This is true whether the secrets are named explicitly or discovered by a regex sweep — the CI runner has the raw key sitting in its environment, in cleartext, for the whole job.
That's the architectural weak point KnoxCall is built to remove, and it's worth being precise about what that does and doesn't mean here. An egress proxy that injects the real provider credential at the network wire — so the application process, the CI runner, and any AI agent calling out to a provider API only ever hold a short-lived, scoped reference rather than the actual AWS or OpenAI key — would not have stopped the account takeover, the workflow injection, or the attacker's ability to run arbitrary code in that pipeline. A hijacked maintainer token still gets you a malicious commit either way.
What it does change is the payoff. If the runner's environment only ever contains a reference token that's meaningless outside KnoxCall's own gateway, then grep-and-curl has nothing live to find. The named-secret theft, the regex sweep of the working tree, and the adjacent-AWS-key trick all depend on a real, usable credential being present somewhere the workflow can read. Remove that credential from the runner entirely and the exfiltration step fails even though everything upstream of it — the stolen PAT, the injected workflow, the plain-HTTP callback — still succeeds exactly as GhostAction's authors designed it.
This is also why credential scope and lifetime matter independently of where the key lives: a scoped, short-lived, egress-bound credential limits blast radius even in architectures that haven't fully removed keys from runners. For teams building out that posture, our security overview and AI gateway pages cover how credential injection at the edge works in practice.
What to actually do about it
Whether or not your org is on GitGuardian's or Socket's published lists, GhostAction's indicators are public and cheap to check for:
- Search your organization's repositories for workflow files named
security-audit.ymlorgithub_actions_security.ymladded since August 2026, and for any outbound reference to193.32.204.199. - Audit commits that land directly on a default branch from a maintainer identity, bypassing pull request review — that's the injection pattern in every documented wave.
- Rotate every secret a compromised repository's workflows could read, not just the ones confirmed stolen; reconnaissance happens before the named theft, so the attacker likely enumerated more than they took.
- Scan full git history, not just the current branch, with a tool like gitleaks or trufflehog — the October variant proves attackers are already doing this against you.
- Revoke and reissue personal access tokens for maintainers, and move toward fine-grained, short-lived tokens or GitHub App installation tokens instead of classic PATs where possible.
What we still don't know
Be skeptical of any writeup, including this one, that claims full certainty about GhostAction's origins. GitGuardian has not publicly attributed the campaign to a named threat actor, and the exact method by which the 2026 maintainer tokens leaked has not been confirmed — the infostealer-log theory is a plausible, commonly-cited inference from researchers at StepSecurity, not a confirmed forensic finding. It's also not yet clear whether the August–September wave GitGuardian tracked and the October burst Socket documented, which GitGuardian itself frames as a continuation of the same campaign, were run by the same operators or by copycats reusing a public technique. Treat the "500+ accounts, tens of thousands of repositories" figure as a rapidly moving number from an active investigation rather than a final tally.