From 58dad275fbd0b39a4a7d0ac8bb0bc108e4fc3f7e Mon Sep 17 00:00:00 2001 From: Ryan Bas Date: Mon, 24 Nov 2025 16:20:25 -0700 Subject: [PATCH 1/4] fix: conditionally append NPM_TOKEN to .npmrc for trusted publishing support MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The .npmrc generation now intelligently handles both traditional NPM token authentication and trusted publishing scenarios: - Only appends auth token to .npmrc when NPM_TOKEN is defined (not undefined) - Uses strict comparison (!== undefined) instead of truthy checks - Provides informative logging when no NPM_TOKEN is present - Maintains full backward compatibility with existing workflows This fixes issues with trusted publishing where OIDC tokens from GitHub Actions are used instead of NPM_TOKEN, preventing 'undefined' from being written to the registry auth configuration. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude --- .changeset/npmrc-trusted-publishing.md | 7 +++++++ src/index.ts | 20 +++++++++++++++----- 2 files changed, 22 insertions(+), 5 deletions(-) create mode 100644 .changeset/npmrc-trusted-publishing.md diff --git a/.changeset/npmrc-trusted-publishing.md b/.changeset/npmrc-trusted-publishing.md new file mode 100644 index 00000000..637502a3 --- /dev/null +++ b/.changeset/npmrc-trusted-publishing.md @@ -0,0 +1,7 @@ +--- +"@changesets/action": patch +--- + +fix: conditionally append NPM_TOKEN to .npmrc for trusted publishing support + +The .npmrc generation now intelligently handles both traditional NPM token authentication and trusted publishing scenarios by only appending the auth token when NPM_TOKEN is defined. This prevents 'undefined' from being written to the registry configuration when using OIDC tokens from GitHub Actions trusted publishing. diff --git a/src/index.ts b/src/index.ts index 1b0f63ab..61aa2efd 100644 --- a/src/index.ts +++ b/src/index.ts @@ -68,6 +68,8 @@ const getOptionalInput = (name: string) => core.getInput(name) || undefined; ); let userNpmrcPath = `${process.env.HOME}/.npmrc`; + const npmToken = process.env.NPM_TOKEN; + if (await fileExists(userNpmrcPath)) { core.info("Found existing user .npmrc file"); const userNpmrcContent = await fs.readFile(userNpmrcPath, "utf8"); @@ -79,20 +81,28 @@ const getOptionalInput = (name: string) => core.getInput(name) || undefined; core.info( "Found existing auth token for the npm registry in the user .npmrc file" ); - } else { + } else if (npmToken !== undefined) { core.info( "Didn't find existing auth token for the npm registry in the user .npmrc file, creating one" ); await fs.appendFile( userNpmrcPath, - `\n//registry.npmjs.org/:_authToken=${process.env.NPM_TOKEN}\n` + `\n//registry.npmjs.org/:_authToken=${npmToken}\n` + ); + } else { + core.info( + "No NPM_TOKEN found and no existing auth token - assuming trusted publishing or npm is already authenticated" ); } - } else { - core.info("No user .npmrc file found, creating one"); + } else if (npmToken !== undefined) { + core.info("No user .npmrc file found, creating one with NPM_TOKEN"); await fs.writeFile( userNpmrcPath, - `//registry.npmjs.org/:_authToken=${process.env.NPM_TOKEN}\n` + `//registry.npmjs.org/:_authToken=${npmToken}\n` + ); + } else { + core.info( + "No user .npmrc file found and no NPM_TOKEN provided - assuming trusted publishing or npm is already authenticated" ); } From 5525a5cc0b094ee6a76ae43dee1ba06f2a04d3b2 Mon Sep 17 00:00:00 2001 From: Ryan Bas <18267769+ryanbas21@users.noreply.github.com> Date: Wed, 26 Nov 2025 11:23:28 -0700 Subject: [PATCH 2/4] Update src/index.ts MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Mateusz Burzyński --- src/index.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/index.ts b/src/index.ts index 61aa2efd..2ed8c617 100644 --- a/src/index.ts +++ b/src/index.ts @@ -95,7 +95,7 @@ const getOptionalInput = (name: string) => core.getInput(name) || undefined; ); } } else if (npmToken !== undefined) { - core.info("No user .npmrc file found, creating one with NPM_TOKEN"); + core.info("No user .npmrc file found, creating one with NPM_TOKEN used as auth token"); await fs.writeFile( userNpmrcPath, `//registry.npmjs.org/:_authToken=${npmToken}\n` From f2960fb427d29b3a50b8842a2f22fb5c95e574a5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Mateusz=20Burzy=C5=84ski?= Date: Tue, 27 Jan 2026 23:05:31 +0100 Subject: [PATCH 3/4] simplify --- src/index.ts | 57 ++++++++++++++++++++++++++-------------------------- 1 file changed, 28 insertions(+), 29 deletions(-) diff --git a/src/index.ts b/src/index.ts index 2ed8c617..2f05db4e 100644 --- a/src/index.ts +++ b/src/index.ts @@ -67,42 +67,41 @@ const getOptionalInput = (name: string) => core.getInput(name) || undefined; "No changesets found. Attempting to publish any unpublished packages to npm" ); - let userNpmrcPath = `${process.env.HOME}/.npmrc`; - const npmToken = process.env.NPM_TOKEN; - - if (await fileExists(userNpmrcPath)) { - core.info("Found existing user .npmrc file"); - const userNpmrcContent = await fs.readFile(userNpmrcPath, "utf8"); - const authLine = userNpmrcContent.split("\n").find((line) => { - // check based on https://github.com/npm/cli/blob/8f8f71e4dd5ee66b3b17888faad5a7bf6c657eed/test/lib/adduser.js#L103-L105 - return /^\s*\/\/registry\.npmjs\.org\/:[_-]authToken=/i.test(line); - }); - if (authLine) { - core.info( - "Found existing auth token for the npm registry in the user .npmrc file" - ); - } else if (npmToken !== undefined) { + if (process.env.NPM_TOKEN) { + const userNpmrcPath = `${process.env.HOME}/.npmrc`; + + if (await fileExists(userNpmrcPath)) { + core.info("Found existing user .npmrc file"); + const userNpmrcContent = await fs.readFile(userNpmrcPath, "utf8"); + const authLine = userNpmrcContent.split("\n").find((line) => { + // check based on https://github.com/npm/cli/blob/8f8f71e4dd5ee66b3b17888faad5a7bf6c657eed/test/lib/adduser.js#L103-L105 + return /^\s*\/\/registry\.npmjs\.org\/:[_-]authToken=/i.test(line); + }); + if (authLine) { + core.info( + "Found existing auth token for the npm registry in the user .npmrc file" + ); + } else { + core.info( + "Didn't find existing auth token for the npm registry in the user .npmrc file, creating one" + ); + await fs.appendFile( + userNpmrcPath, + `\n//registry.npmjs.org/:_authToken=${process.env.NPM_TOKEN}\n` + ); + } + } else { core.info( - "Didn't find existing auth token for the npm registry in the user .npmrc file, creating one" + "No user .npmrc file found, creating one with NPM_TOKEN used as auth token" ); - await fs.appendFile( + await fs.writeFile( userNpmrcPath, - `\n//registry.npmjs.org/:_authToken=${npmToken}\n` - ); - } else { - core.info( - "No NPM_TOKEN found and no existing auth token - assuming trusted publishing or npm is already authenticated" + `//registry.npmjs.org/:_authToken=${process.env.NPM_TOKEN}\n` ); } - } else if (npmToken !== undefined) { - core.info("No user .npmrc file found, creating one with NPM_TOKEN used as auth token"); - await fs.writeFile( - userNpmrcPath, - `//registry.npmjs.org/:_authToken=${npmToken}\n` - ); } else { core.info( - "No user .npmrc file found and no NPM_TOKEN provided - assuming trusted publishing or npm is already authenticated" + "No NPM_TOKEN found - assuming trusted publishing or npm is already authenticated" ); } From 51d41feee44836d9f9875775b27bc07e0e175491 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Mateusz=20Burzy=C5=84ski?= Date: Tue, 27 Jan 2026 23:11:31 +0100 Subject: [PATCH 4/4] tweak changeset --- .changeset/npmrc-trusted-publishing.md | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/.changeset/npmrc-trusted-publishing.md b/.changeset/npmrc-trusted-publishing.md index 637502a3..f9987fe7 100644 --- a/.changeset/npmrc-trusted-publishing.md +++ b/.changeset/npmrc-trusted-publishing.md @@ -2,6 +2,4 @@ "@changesets/action": patch --- -fix: conditionally append NPM_TOKEN to .npmrc for trusted publishing support - -The .npmrc generation now intelligently handles both traditional NPM token authentication and trusted publishing scenarios by only appending the auth token when NPM_TOKEN is defined. This prevents 'undefined' from being written to the registry configuration when using OIDC tokens from GitHub Actions trusted publishing. +The `.npmrc` generation now intelligently handles both traditional NPM token authentication and trusted publishing scenarios by only appending the auth token when `NPM_TOKEN` is defined. This prevents 'undefined' from being written to the registry configuration when using OIDC tokens from GitHub Actions trusted publishing.