What the proxy does
Each organisation sets its own policy. It applies to every laptop, runner and Dockerfile that pulls through the proxy.
The same package checks on merge requestsMopokeHQ runs a registry proxy for npm, Composer and Docker, hosted and isolated per organisation. Your builds pull through it. New versions wait out a cooldown, known-malicious packages never arrive, and every download is logged.
The supply chain proxy is a paid add-on to MopokeHQ.
Most of these versions were live for hours, not weeks. The builds that got hit were the ones that installed inside that window. A registry you control can keep you out of it.
| Date | What | How | Source |
|---|---|---|---|
| 8 Sep 2025 | chalk, debug and 16 other packagesnpm | A maintainer was phished with a fake 2FA reset. The malicious versions hijacked crypto wallet transactions in browsers. | StepSecurity |
| Sep 2025 | Shai-Hulud wormnpm | Stole GitHub and cloud credentials, then published infected versions of the victim’s other packages. CISA advised pinning and rotating credentials. | CISA |
| 31 Mar 2026 | axios 1.14.1 and 0.30.4npm | A maintainer account takeover added a new dependency whose postinstall script dropped a remote access trojan. The versions were live for about three hours. | CSA Singapore |
| 11 May 2026 | 42 @tanstack packagesnpm | A poisoned CI cache let attackers publish 84 malicious versions through the project’s own release pipeline. They carried valid provenance. | TanStack |
| 22 May 2026 | Laravel-Lang packagesComposer | Attackers rewrote existing Git tags so old version numbers pointed at a credential stealer loaded through Composer autoload. | BleepingComputer |
The axios versions were removed about three hours after they were published. A 24 hour cooldown would have kept both out of every install that resolved through it.
Each organisation sets its own policy. It applies to every laptop, runner and Dockerfile that pulls through the proxy.
The same package checks on merge requestsYour private packages stay in your own GitLab package registry. Private scopes never resolve to a public registry, so nobody can publish a public package with your internal name and have your build pick it up.
That attack is called dependency confusion, and it matters on GitLab in particular: by default, GitLab’s npm registry redirects requests for packages it cannot find to npmjs.com.
One file per ecosystem. Commit it with the project, or set it once on your runners. The exact hosts and your token appear in MopokeHQ when you switch the proxy on; the ones below are placeholders.
# Public packages through the MopokeHQ proxyregistry=https://npm.your-org.mopokehq.example///npm.your-org.mopokehq.example/:_authToken=${NPM_TOKEN}# Your private scope stays on your GitLab package registry@your-scope:registry=https://gitlab.example.com/api/v4/groups/123/-/packages/npm/{ "repositories": [ { "type": "composer", "url": "https://gitlab.example.com/api/v4/group/123/-/packages/composer/packages.json" }, { "type": "composer", "url": "https://composer.your-org.mopokehq.example" }, { "packagist.org": false } ]}FROM docker.your-org.mopokehq.example/library/node:22npm, pnpm, Yarn, Bun and Composer each have their own cooldown setting, with their own names and units. Older npm versions ignore the setting without warning. Docker has no setting at all.
Set the client settings anyway; they cost nothing. The proxy adds one policy, set once, that holds whatever client version a laptop or runner happens to have.
| Client | Setting | Counts in |
|---|---|---|
| npm 11.10+ | min-release-age | Days |
| pnpm 10.16+ | minimumReleaseAge | Minutes |
| Bun | install.minimumReleaseAge | Seconds |
| Composer 2.11 RC | policy.cooldown | A duration |
| Docker | None | n/a |
The proxy decides what can be installed. The rest of MopokeHQ keeps watching what already was.
How MopokeHQ worksCommit a lockfile and install with npm ci in CI. Set a minimum release age so brand-new versions wait before they install. Use phishing-resistant MFA on npm and GitHub accounts, and rotate tokens after any incident. A registry proxy adds one more layer: it applies a cooldown and blocks known-malicious packages for every machine that pulls through it.
Yes, with care. Malicious versions are usually removed once reported, often within hours. The risk is installing during those hours. A cooldown, a lockfile and a check on brand-new packages cover most of that window.
A setting that skips package versions younger than a set age. npm calls it min-release-age and counts days (npm 11.10.0 and later). pnpm calls it minimumReleaseAge and counts minutes, with 24 hours as the default from pnpm 11. Composer added a cooldown policy in its 2.11 release candidate. MopokeHQ applies the same idea at the registry, so it covers every client version.
An attacker publishes a public package with the same name as one of your private packages. If your package manager checks the public registry, it may install theirs. With MopokeHQ, private scopes never resolve publicly, and your private packages stay in your GitLab package registry.
Yes. The proxy covers npm, Composer (Packagist) and Docker/OCI images, with one policy per organisation.
It runs highly available in Sydney. If you ever need to bypass it, there is a documented break-glass switch.
No. Audits look for known vulnerabilities in what you already installed. The proxy decides what can be installed in the first place. MopokeHQ’s continuous matching covers the audit side.
The supply chain proxy is a paid add-on, priced separately from your MopokeHQ plan.