# `@vpms/design-system` - internal-scope dependency-confusion with preinstall env-var exfil to Pipedream

> On 2026-06-25 between 15:52 UTC and 17:14 UTC, an operator published four versions of `@vpms/design-system` (`0.1.3`, `1.0.0`, `1.0.1`, `1.1.2`) as a dependency-confusion attack against the internal `@vpms` scope. The preinstall script iterates `process.env` and harvests every variable whose name contains `SECRET`, `TOKEN`, `PASSWORD`, `KEY`, or `CREDENTIAL`, along with hostname, username, and process details, then exfiltrates the payload to a hardcoded Pipedream webhook at `eov0bmnid410yqf.m.pipedream.net`. npm-support replaced all four versions with a `0.0.1-security` holder on 2026-06-29.

- Published: 2026-06-25
- Severity: high
- Kind: Dependency confusion - A package published on the public registry under a name guessed from a company's private registry, usually at a sentinel version such as 0.0.0 or 99.99.0, so a misconfigured resolver pulls it instead of the internal one. Many are bug-bounty or penetration-test probes whose only payload is a beacon with the hostname.
- Ecosystems: npm
- Scope: 1 package, 4 compromised versions
- Tags: dependency-confusion, credential-theft, ci-cd-compromise
- Also known as: vpms design-system pentest
- Detected by: Amazon Inspector, OpenSSF Package Analysis, GitHub Security Advisory
- Incident ID: npm-2026-06-25-vpms-design-system-pipedream

## Affected packages (1)

Only the exact versions listed were named by the source advisories. Other versions are not implicated.

| Package | Ecosystem | Compromised versions |
|---|---|---|
| [@vpms/design-system](https://dependencywatch.io/package/npm/@vpms/design-system) | npm | 0.1.3, 1.0.0, 1.0.1, 1.1.2 |

## What happened

On 2026-06-25 between 15:52:53 UTC and 17:14:47 UTC, an operator published four versions of `@vpms/design-system` to the public npm registry - `1.0.0`, `1.0.1`, `1.1.2`, and `0.1.3` (the out-of-order final publish backfills a lower version to catch consumers using `^0.1` ranges). The package title and README masquerade it as a "pentest design system" but the shipped tarball contains no design-system code; the entire payload is the preinstall lifecycle hook.

## Preinstall env-var exfiltration

The `package.json` declares a `preinstall` script that runs before any user code on every `npm install`. The script iterates `process.env`, filters variables whose names contain any of the substrings `SECRET`, `TOKEN`, `PASSWORD`, `KEY`, or `CREDENTIAL` (case-insensitive), and collects them alongside host identifiers (`os.hostname()`, `os.userInfo()`, and the full process argv). The payload is JSON-stringified and POSTed via HTTPS to a hardcoded Pipedream webhook at `https://eov0bmnid410yqf.m.pipedream.net`.

The substring filter catches a wide spectrum of CI / developer environment variables - `GITHUB_TOKEN`, `NPM_TOKEN`, `AWS_ACCESS_KEY_ID` / `AWS_SECRET_ACCESS_KEY`, `GCP_SERVICE_ACCOUNT_KEY`, `STRIPE_SECRET_KEY`, `SLACK_BOT_TOKEN`, `DATABASE_PASSWORD`, generic `*_API_KEY` patterns, and so on. Anyone whose `npm install` runs with these populated (CI runners almost always have several; developer machines often have a few via `direnv` or `.envrc`) leaks them to the operator in a single round-trip.

## Dependency-confusion targeting

The `@vpms` scope is unregistered in the public npm registry, so any internal `@vpms/design-system` package living on a private registry that is consulted alongside `registry.npmjs.org` is a dependency-confusion target. The operator's use of `1.0.0` → `1.0.1` → `1.1.2` version bumps targets the common SemVer range `^1.0.0` that internal consumers would write in their `package.json`. The trailing `0.1.3` publish backfills the rare consumer pinning a `^0.1` range. Detection sources include Amazon Inspector, OpenSSF Package Analysis, and GitHub Security Advisory, ingested by OSSF malicious-packages as `MAL-2026-6467`.

## Disclosure timeline

- **2026-06-25 15:52:53 UTC** - `@vpms/design-system@1.0.0` published.
- **2026-06-25 16:07:57 UTC** - `@vpms/design-system@1.0.1`.
- **2026-06-25 16:23:58 UTC** - `@vpms/design-system@1.1.2`.
- **2026-06-25 17:14:47 UTC** - `@vpms/design-system@0.1.3` (the out-of-order backfill).
- **2026-06-29 02:52:29 UTC** - npm-support replaces the package with a `0.0.1-security` holder; OSSF publishes `MAL-2026-6467`.

## Impact

- Install-time credential harvest - `preinstall` lifecycle hook runs before any user code on `npm install`, iterates `process.env`, and exfiltrates every variable whose name contains the substrings `SECRET`, `TOKEN`, `PASSWORD`, `KEY`, or `CREDENTIAL` to an attacker-controlled Pipedream HTTPS endpoint
- Companion harvest of host identifiers (`os.hostname()`, `os.userInfo()`, full process argv) lets the operator correlate stolen env vars to the specific developer machine or CI runner that produced them, enabling targeted re-use
- Dependency-confusion vector - the `@vpms` scope was being squatted in the public npm registry to intercept builds that resolve `@vpms/design-system` without an enforced scope-to-registry pin, so internal CI / private-registry consumers of a real `@vpms` package were the intended victims
- Package masquerades as a "pentest design system"; the README contains no design-system functionality and the entire shipped tarball is the preinstall exfiltration primitive

## What to do

1. Remove every reference to `@vpms/design-system` from `package.json` / lockfiles / CI image layers; the name now serves a `0.0.1-security` holder, so previously-pinned `0.1.3` / `1.0.0` / `1.0.1` / `1.1.2` no longer resolve
2. If your organization legitimately uses an internal `@vpms` scope: enforce a scope-to-registry pin (`@vpms:registry=https://internal-registry.example.com` in `.npmrc`) so the public registry is never consulted for that scope on any developer machine or CI runner
3. Treat any host that ran `npm install` against `@vpms/design-system` as having exfiltrated every `*SECRET*` / `*TOKEN*` / `*PASSWORD*` / `*KEY*` / `*CREDENTIAL*` environment variable: rotate npm tokens, GitHub Actions tokens, AWS / GCP / Azure tokens, SSH passphrases, database passwords, and any third-party API keys reachable from that runtime, from a separate clean device
4. Block `*.m.pipedream.net` at egress for CI runners and developer endpoints; hunt firewall and DNS logs for outbound HTTPS to `eov0bmnid410yqf.m.pipedream.net` since 2026-06-25
5. Audit other `@vpms`-scoped names in the public registry - the operator may publish additional siblings under the same scope to widen the dependency-confusion blast radius

## Check your own dependencies

- Check a package-lock.json against this incident: https://dependencywatch.io/check/package-lock-json

The scan runs entirely in the browser; lockfile contents are never uploaded.

## References

- [MAL-2026-6467 - @vpms/design-system Pipedream exfil](https://github.com/ossf/malicious-packages/blob/main/osv/malicious/npm/%40vpms/design-system/MAL-2026-6467.json) - OpenSSF Malicious Packages
- [@vpms/design-system on npm](https://www.npmjs.com/package/@vpms/design-system) - npm

---

Canonical page: https://dependencywatch.io/incident/npm-2026-06-25-vpms-design-system-pipedream
Markdown version: https://dependencywatch.io/incident/npm-2026-06-25-vpms-design-system-pipedream.md
Site index for agents: https://dependencywatch.io/llms.txt
DependencyWatch.io is operated by Precursor Security (https://precursorsecurity.com).
