diff --git a/lib/utils/oidc.js b/lib/utils/oidc.js index d647721b10153..7f453cb122ed7 100644 --- a/lib/utils/oidc.js +++ b/lib/utils/oidc.js @@ -30,7 +30,7 @@ async function oidc ({ packageName, registry, opts, config }) { /** @see https://github.com/watson/ci-info/blob/v4.2.0/vendors.json#L161C13-L161C22 */ ciInfo.GITLAB )) { - log.silly('oidc', 'Skipped because not running in a supported CI environment') + log.silly('oidc', 'Skipped because unsupported CI environment') return undefined } @@ -159,13 +159,13 @@ async function oidc ({ packageName, registry, opts, config }) { }) } catch (error) { if (error?.body?.message) { - log.verbose('oidc', `Failed with registry body response error message "${error.body.message}"`) + log.verbose('oidc', `Failed with body message "${error.body.message}"`) } return undefined } if (!response?.token) { - log.verbose('oidc', 'Failed with token exchange missing token in response body') + log.verbose('oidc', 'Failed because token exchange was missing the token in the response body') return undefined } /* @@ -178,8 +178,7 @@ async function oidc ({ packageName, registry, opts, config }) { config.set(authTokenKey, response.token, 'user') log.verbose('oidc', `Successfully retrieved and set token`) } catch (error) { - /* istanbul ignore next */ - log.verbose('oidc', 'Failed checking config', error) + log.verbose('oidc', `Failure with message "${error?.message || 'Unknown error'}"`) } return undefined } diff --git a/test/fixtures/mock-oidc.js b/test/fixtures/mock-oidc.js index 03a35522f7345..2b9302aa5b460 100644 --- a/test/fixtures/mock-oidc.js +++ b/test/fixtures/mock-oidc.js @@ -80,8 +80,11 @@ const mockOidc = async (t, { ciInfo.GITLAB = GITLAB }) - const { npm, registry, joinedOutput } = await loadNpmWithRegistry(t, { - config, + const { npm, registry, joinedOutput, logs } = await loadNpmWithRegistry(t, { + config: { + loglevel: 'silly', + ...config, + }, prefixDir: { 'package.json': JSON.stringify({ name: packageName, @@ -128,7 +131,7 @@ const mockOidc = async (t, { }) } - return { npm, joinedOutput } + return { npm, joinedOutput, logs, ACTIONS_ID_TOKEN_REQUEST_URL } } const oidcPublishTest = (opts) => { diff --git a/test/lib/commands/publish.js b/test/lib/commands/publish.js index 7a285ecbb2488..530a097d07542 100644 --- a/test/lib/commands/publish.js +++ b/test/lib/commands/publish.js @@ -5,8 +5,9 @@ const pacote = require('pacote') const Arborist = require('@npmcli/arborist') const path = require('node:path') const fs = require('node:fs') -const { githubIdToken, gitlabIdToken, oidcPublishTest } = require('../../fixtures/mock-oidc') +const { githubIdToken, gitlabIdToken, oidcPublishTest, mockOidc } = require('../../fixtures/mock-oidc') const { sigstoreIdToken } = require('@npmcli/mock-registry/lib/provenance') +const mockGlobals = require('@npmcli/mock-globals') const pkg = '@npmcli/test-package' const token = 'test-auth-token' @@ -1135,6 +1136,52 @@ t.test('oidc token exchange - no provenance', t => { }, })) + t.test('global try / catch failure via malformed url', oidcPublishTest({ + config: { + '//registry.npmjs.org/:_authToken': 'existing-fallback-token', + }, + oidcOptions: { + github: true, + // malformed url should trigger a global try / catch + ACTIONS_ID_TOKEN_REQUEST_URL: '//github.com', + }, + publishOptions: { + token: 'existing-fallback-token', + }, + })) + + t.test('global try / catch failure via throw non Error', async t => { + const { npm, logs, joinedOutput, ACTIONS_ID_TOKEN_REQUEST_URL } = await mockOidc(t, { + config: { + '//registry.npmjs.org/:_authToken': 'existing-fallback-token', + }, + oidcOptions: { + github: true, + }, + publishOptions: { + token: 'existing-fallback-token', + }, + }) + + class URLOverride extends URL { + constructor (...args) { + const [url] = args + if (url === ACTIONS_ID_TOKEN_REQUEST_URL) { + throw 'Specifically throwing a non errror object to test global try / catch' + } + super(...args) + } + } + + mockGlobals(t, { + URL: URLOverride, + }) + + await npm.exec('publish', []) + t.match(joinedOutput(), '+ @npmcli/test-package@1.0.0') + t.ok(logs.includes('verbose oidc Failure with message "Unknown error"')) + }) + t.test('default registry success gitlab', oidcPublishTest({ oidcOptions: { gitlab: true, NPM_ID_TOKEN: gitlabPrivateIdToken }, config: {