Sha1-Hulud 2.0 - The Second Coming: What You Need To Know

By
Artur Oleyarsh
December 1, 2025
Share this post

Earlier this year on September 25, the open-source software community was hit by a supply chain attack called Sha1-Hulud, in which a self-replicating worm heavily impacted the NPM ecosystem by compromising hundreds of open-source software packages.

After gaining initial access to a victim’s endpoint via the compromised third party package, the malicious script scanned the environment for credentials including GCP, AWS, Azure, and GitHub Personal Access Tokens. Once found, the data was exfiltrated to the endpoint controlled by the threat actor. On November 24th, Sha1-Hulud returned with a new version. Here is what you need to know.

Sha1-Hulud 2.0: What happened?

  • A new variant of Sha1-Hulud Software Supply Chain attack emerged
  • Over 25K GitHub repositories were affected
  • Hundreds of NPM packages were infected, including few of the famous projects
  • Thousands of files were exfiltrated containing:
    • NPM tokens
    • Cloud Service Providers keys (AWS, GCP, Azure)
    • GitHub tokens
    • GitHub actions secrets
  • Sha1-Hulud 2.0 is able to self-replicate and infect additional projects in the ecosystem

How the Sha1-Hulud 2.0 Attack Works

Sha1-Hulud 2.0 uses a layered, multi-stage infection process designed to blend into normal package installation workflows. By abusing npm lifecycle scripts, and harvesting cloud and GitHub credentials, the worm can silently compromise a developer’s environment and spread across the broader ecosystem.

Step 1: package.json

When a package is compromised, two files are added to the root directory of the package:

  1. setup_bun.js
  2. bun_environment.js

The infection is triggered by the following preinstall script that is added to package.json of the compromised package.

After a victim executes npm install, npm will execute lifecycle scripts where preinstall scripts will execute first (before the actual install). The same behavior will take place even if the victim is not directly interacting with the infected package and the package is coming as a transitive dependency; or if the installation fails, the preinstall script will run first.

Step 2: setup_bun.js

setup_bun.js serves as an entry point. Its main objective is:

  • Check if the Bun (JavaScript runtime) is installed on the victim’s endpoint
    • This is an interesting behavior that was likely intended to avoid using Node.js and its protections, such as warnings about suspicious lifecycle scripts.
  • Depending on the operating system, it downloads and installs Bun if not present

  • Reload user’s PATH to make sure Bun binary is useable
  • Run bun_environment.js using Bun

Step 3: bun_environment.js

This is a heavily obfuscated JS file, over 200K lines of obfuscated code, and it is the heart of a Sha1-Hulud 2.0 worm. Its purpose is to:

  • Fingerprint victims environment
  • Collect environment variables
  • Enumerate local projects and Git repositories
  • There is an indication that Sha1-Hulud 2.0 is utilizing TruffleHog open-source tool secrets scanner to scan for secrets
    • Scan for cloud service providers related secrets (GCP, AWS, Azure)

  • Abusing NPM tokens - once it obtained victim’s NPM tokens Sha1-Hulud 2.0 has control over the projects maintained by the victim, which allows the worm to perform a self-propagation step by updating and publishing packages with same preinstall script

  • If no GitHub or NPM tokens are found, it will fallback to deleting data in the victim's endpoint home directory, depending on the operating system.

Step 4: Exfiltration via Public GitHub Repositories

  • The data collected by the NPM worm is exfiltrated via a public GitHub repository
    • A random 18 characters long string generated for a repository name which is published as a public repository under a compromised account with a fixed description name Sha1-Hulud: The Second Coming.
    • The repository contains several files with a double encoded Base64 string containing the collected victim’s data
      • cloud.json 
      • contents.json
      • environment.json
      • truffleSecrets.json
    • If no GitHub credentials are found, the worm will use other victims’ compromised GitHub credentials. This is why we see many different random repositories under the same account. One compromised account can publish several repositories containing exfiltrated data of several other victims.
    • github/workflows directory containing discussion.yaml file

  • discussion.yaml
    • The injected workflow by the Sha1-Hulud will be triggered whenever someone creates or updates a GitHub discussion
    • Forced execution on a self-hosted runner - If a victim configured self-hosted runners, Github Actions runners will run arbitrary code supplied by the attacker
    • RUNNER_TRACKING_ID: 0 - known trick to suppress runner telemetry or GitHub tracking features
    • run: echo ${{ github.event.discussion.body }} - used to verify code execution. echo can be replaced with any arbitrary command

IOCs (Indicators of Compromise) for SHA1-Hulud 2.0

  • Preinstall scripts in package.json files
  • Unintended installation of Bun software
  • Public GitHub repository created with 18 digit random string under your account
  • setup_bun.js and bun_environment.js files present on an endpoint

What to Do if You Are Affected by SHA1-Hulud 2.0

Remediations steps should include the following:

  • Remove the infected packages - scan across all endpoints you suspect that might be affected
  • Rotate and revoke any affected credentials
  • Temporary restrict repository creation until the investigation is finished
  • Delete public repositories that were created by the Sha1-Hulud 2.0 worm
  • Apply third party dependencies hygiene:
    • Constantly scan transitive dependencies for malicious activity
    • Use reliable sources for installing third party OSS (commit hashes, trusted versions etc)
    • If using NPM, think of applying npm ci instead of npm install for automated environments
  • Check for additional connected environments and accounts that might be affected

How can Minimus help?

After reading how Sha1-Hulud 2.0 is infecting projects across the NPM ecosystem and the possible damage, you probably understand that an endpoint can be compromised even if it does not interact with the infected package directly. It is enough to build an artifact containing an infected package as a transitive dependency to get infected by the NPM worm, and we all know how easy it is to miss that!

At Minimus, we make sure our images are built using trusted and verified OSS and third party components. By controlling the entire supply chain, endpoints utilizing our images are protected from such supply chain attacks. This eliminates a major source of stress for DevSecOps teams and developers, allowing them to rely on images that are secure by default rather than struggling to build safe, non-vulnerable image versions on their own. 

Try our secure-by-default images today and minimize your exposure to supply chain threats.

Share this post
Artur Oleyarsh
Security Researcher
Sign up for minimus

Avoid over 97% of container CVEs

Access hundreds of hardened images, secure Helm charts, the Minimus custom image builder, and more.