Npm creates token that publishes package only after human review
New granular access token type from npm separates who ships the version from who approves the publication, closing a classic gap of leaked tokens in CI/CD.

Anyone who has ever set up automated npm package publishing in CI knows the dilemma: the token the workflow uses to run npm publish needs full publish power, or the automation breaks. The problem is that this same token, if it leaks from a log, a misconfigured secret, or a compromised dependency in the pipeline itself, becomes a blank check for someone to publish a malicious version of your package without anyone needing to type a 2FA code.
The GitHub Changelog announced on September 18 a new permission type for npm granular access tokens: Read and write (stage only). In practice, it's the separation of roles that was missing between "generating the artifact" and "deciding it goes to the registry".
How it works in practice
With a stage-only token, the workflow no longer runs npm publish. It runs npm stage publish, which packages and sends the version to npm, but it stays held as a draft awaiting approval. A human maintainer reviews this draft and approves the release with 2FA. If someone tries to use that same token to run npm publish directly, npm rejects the call, even if the token is configured to bypass 2FA in automation. It's this detail that changes the threat model: the CI token alone is no longer enough to put code into production on the registry.
It's worth noting that the stage-only token isn't a "weak" token: it still keeps other write permissions, like moving dist-tags and deprecating versions. In other words, it remains a sensitive token and needs the same secret handling as any publish token, except that the final step of "releasing the version to the world" is out of its reach.
Prerequisites before migrating
Before changing anything in the workflow, check whether the environment meets npm's minimum requirements:
- Publish access to the package you want to protect.
- 2FA enabled on the npm account of whoever will approve the release.
- npm CLI version 11.15.0 or higher.
- Node.js 22.14.0 or higher.
If your pipeline still runs on an image with Node 18 or an older Node 20 LTS, this is the first real blocker: you'll need to update the build image before even testing the new flow.
The path I'd follow to migrate a pipeline
In a typical project with automated publishing via GitHub Actions, the roadmap would look like this:
- Generate the new token on npmjs.com, on the granular access tokens screen, choosing Read and write (stage only) and limiting the scope to the packages the workflow actually publishes (never create an "umbrella" stage-only token for the whole org if the workflow only handles one package).
- Swap the secret in the repository, replacing the value of
NPM_TOKEN(or whatever name you use) with the new stage-only token. - Edit the publish step in the workflow, changing the command from
npm publishtonpm stage publish. This is usually the only code change needed in CI. - Agree with the team on who will approve the staged versions. This is the step that tends to stall in small teams: if only one person has 2FA configured and they're on vacation, the release stays stuck until someone reviews it. It's worth defining a second approver before flipping the switch.
- Run a test release on a low-risk package (an internal lib, a sample package) before applying it to the main package, just to validate that the review flow is working as expected.
The staged publishing documentation covers the approval step in more depth than fits here, and it's worth reading before touching production: https://docs.npmjs.com has the specific section linked in the original changelog.
What changes and what doesn't
Anyone already using publish tokens today doesn't need to do anything: the change is opt-in and doesn't affect existing tokens or their ability to publish directly. The point is that this is clearly a bridge, not the final destination. The changelog itself reaffirms that npm is aiming for January 2027 to remove direct publishing via tokens with 2FA bypass. Anyone who relies today on automation with a plain token will need to choose between two routes by then: migrating to trusted publishing (authentication via OIDC, with no long-lived token stored in any secret) or adopting stage-only tokens as a middle ground for those who still can't restructure their pipeline for OIDC.
This second option is what makes the stage-only token interesting for real teams: not everyone has the time or governance to migrate to trusted publishing right now, especially in monorepos with dozens of packages and multiple legacy workflows. The stage-only token delivers an immediate security gain without requiring a full rewrite of the CI architecture.
When it's not worth it (yet)
If your release process already relies on deployment without human intervention, like automated canary releases triggered by a merge to main without anyone's review, the stage-only token introduces friction that may not make sense for your context: someone will need to manually approve every publication, which breaks the promise of
Translated from the Brazilian Portuguese original · Read the original
CodeQL 2.27.1 gets C/C++ queries and Kotlin 2.4.20 support
The version released on September 25, 2026 refines GitHub's static analysis engine with new taint flow models for C/C++, adjustments to Kotlin's K2 compiler, and fixes that reduce false positives across several languages.
