Email us with details. Do not open a public issue.
We publish two npm packages — @alien-id/agent-id-core and
@alien-id/agent-id-vault — and ship four more plugins through the Claude Code
marketplace (agent-id-auth, -git, -proxy, -browser). The marketplace
plugins npm install the two published libraries at runtime, so a supply-chain
compromise of either lib reaches every consumer. We harden in layers; each layer
assumes the layers below it have failed.
- WebAuthn / passkey 2FA only on every npmjs and GitHub account that can publish. TOTP is disabled at the org level (real-time-phishable).
- OIDC trusted publishing is configured per package on npmjs.com → no
long-lived
NPM_TOKENexists in repo secrets.
bunfig.tomlenforces:minimumReleaseAge = 259200— 3-day cooldown. Every 2025-2026 worm was detected within 30 minutes; a 3-day gate is a near-complete consumer shield.exact = true— newly added third-party deps land pinned, no^/~float. (Internal@alien-id/*deps intentionally keep^ranges so the marketplace plugins float onto compatible core/vault patches.)- registry pinned to
https://registry.npmjs.org/(incl. the@alien-idscope).
.npmrcmirrors this for thenpm publishpath and the runtime install hook:ignore-scripts=true,min-release-age=3,audit-signatures=true,save-exact=true,engine-strict=true.package.jsondeclarestrustedDependencies: []— explicit empty allowlist for Bun's lifecycle-script gate.bun.lockis committed; CI runsbun install --frozen-lockfile.
- Default-deny permissions: every workflow declares
permissions: {}at the top level; each job re-grants only what it needs. - Version PR creation and publish are separate jobs.
release.ymlsplits into aversion-prjob (holds onlycontents: write+pull-requests: write, never gated) and apublishjob (holdsid-token: writefor OIDC, gated by thenpm-publishenvironment reviewer, runs the topological publish loop +changeset tag). The OIDC token never coexists with version-bumping install code that processes contributor-supplied manifests — the TanStack/Astro 2025 exfiltration class. There is no build step (plugins are raw.mjs). - A read-only
detectjob decides what each push should do from ground truth (changeset files for the Version PR, registry state for the publish), so nothing reaches the publish gate without a pending release. step-security/harden-runneron every job.blockmode on thedetectandpublishrelease jobs (publish is the only one holdingid-token), with allowlists limited to npmjs, sigstore (publish only), and github.com.auditmode on CI and on theversion-prjob — it holds no OIDC token, and block mode severs the GitHub GraphQL call@changesets/changelog-githubmakes duringchangeset version("Premature close").- GitHub Environment
npm-publishgates only the publish job — required reviewers configured in repo settings. The Version PR is created without environment gating so reviewers see the proposed bumps first. - Every third-party Action is pinned to a commit SHA, with the version in a
trailing comment. Renovate keeps SHAs current via
config:best-practices. - Workflows do not use
pull_request_targetand do not shell-interpolate${{ github.event.* }}. - Monthly cache purge (
purge-cache.yml) — defends against poisoned cache reuse.
- Renovate (
renovate.json) enforces a uniform 3-day cooldown for all dependency types, matching the install-time enforcement inbunfig.tomland.npmrc. Vulnerability alerts bypass cooldown. - SHA-pinned
github-actionsupdates viaconfig:best-practices— any Action bump is a digest change visible in the PR diff. rangeStrategy: pin— Renovate writes exact versions for devDependencies;plugins/**/package.jsonruntime deps keep ranges so consumers can dedupe.
If you depend on @alien-id/* packages, adopt the same defaults — at minimum a
3-day cooldown on npm installs and frozen lockfiles in CI. Our manifests use
exact-version pins for devDependencies to make this easier.
If we suspect one of our published packages is compromised:
- Revoke every npm token and GitHub PAT touching the affected scope.
- Disable the OIDC trusted publisher binding in npmjs settings.
npm deprecate '@alien-id/<pkg>@<bad>' "Compromised — do not use". If within the 72h window, alsonpm unpublish.- Cut a clean patch release that supersedes the bad version, signed via a freshly re-bound OIDC publisher.
- Publish a GitHub Security Advisory with IoCs.
- Post-mortem: which layer failed, which held, what changes.