diff --git a/README.md b/README.md index 7a3d2d19..9157a17f 100644 --- a/README.md +++ b/README.md @@ -53,9 +53,10 @@ Both the [token](https://docs.npmjs.com/getting-started/working_with_tokens) and | `NPM_USERNAME` | Npm username created via [npm adduser](https://docs.npmjs.com/cli/adduser) or on [npmjs.com](https://www.npmjs.com) | | `NPM_PASSWORD` | Password of the npm user. | | `NPM_EMAIL` | Email address associated with the npm user | -| `NPM_CONFIG_USERCONFIG` | Path to non-default .npmrc file | +| `NPM_CONFIG_USERCONFIG` | Path to non-default .npmrc file | +| `NPM_CONFIG__AUTH` | Npm `_auth` configuration parameter set as an [environment variable](https://docs.npmjs.com/cli/v7/using-npm/config) | -Use either `NPM_TOKEN` for token authentication or `NPM_USERNAME`, `NPM_PASSWORD` and `NPM_EMAIL` for legacy authentication +Use either `NPM_TOKEN` for token authentication or `NPM_USERNAME`, `NPM_PASSWORD` and `NPM_EMAIL` (or alternatively `NPM_CONFIG__AUTH` and `NPM_EMAIL`) for legacy authentication ### Options diff --git a/lib/set-npmrc-auth.js b/lib/set-npmrc-auth.js index eef6ee6c..542ab08f 100644 --- a/lib/set-npmrc-auth.js +++ b/lib/set-npmrc-auth.js @@ -9,7 +9,7 @@ const getError = require('./get-error'); module.exports = async ( npmrc, registry, - {cwd, env: {NPM_TOKEN, NPM_CONFIG_USERCONFIG, NPM_USERNAME, NPM_PASSWORD, NPM_EMAIL}, logger} + {cwd, env: {NPM_TOKEN, NPM_CONFIG__AUTH, NPM_CONFIG_USERCONFIG, NPM_USERNAME, NPM_PASSWORD, NPM_EMAIL}, logger} ) => { logger.log('Verify authentication for registry %s', registry); const {configs, ...rcConfig} = rc( @@ -35,6 +35,12 @@ module.exports = async ( `${currentConfig ? `${currentConfig}\n` : ''}_auth = \${LEGACY_TOKEN}\nemail = \${NPM_EMAIL}` ); logger.log(`Wrote NPM_USERNAME, NPM_PASSWORD and NPM_EMAIL to ${npmrc}`); + } else if (NPM_CONFIG__AUTH && NPM_EMAIL) { + await outputFile( + npmrc, + `${currentConfig ? `${currentConfig}\n` : ''}_auth = \${NPM_CONFIG__AUTH}\nemail = \${NPM_EMAIL}` + ); + logger.log(`Wrote NPM_CONFIG__AUTH and NPM_EMAIL to ${npmrc}`); } else if (NPM_TOKEN) { await outputFile( npmrc, diff --git a/test/set-npmrc-auth.test.js b/test/set-npmrc-auth.test.js index 52d427ac..db832c43 100644 --- a/test/set-npmrc-auth.test.js +++ b/test/set-npmrc-auth.test.js @@ -48,6 +48,19 @@ test.serial('Set auth with "NPM_USERNAME", "NPM_PASSWORD" and "NPM_EMAIL"', asyn t.deepEqual(t.context.log.args[1], [`Wrote NPM_USERNAME, NPM_PASSWORD and NPM_EMAIL to ${npmrc}`]); }); +test.serial('Set auth with "NPM_CONFIG__AUTH" and "NPM_EMAIL"', async (t) => { + process.env.HOME = tempy.directory(); + const cwd = tempy.directory(); + process.chdir(cwd); + const npmrc = tempy.file({name: '.npmrc'}); + const env = {NPM_CONFIG__AUTH: 'npm_config__auth', NPM_EMAIL: 'npm_email'}; + + await require('../lib/set-npmrc-auth')(npmrc, 'http://custom.registry.com', {cwd, env, logger: t.context.logger}); + + t.is((await readFile(npmrc)).toString(), `_auth = \${NPM_CONFIG__AUTH}\nemail = \${NPM_EMAIL}`); + t.deepEqual(t.context.log.args[1], [`Wrote NPM_CONFIG__AUTH and NPM_EMAIL to ${npmrc}`]); +}); + test.serial('Preserve home ".npmrc"', async (t) => { process.env.HOME = tempy.directory(); const cwd = tempy.directory(); @@ -147,6 +160,22 @@ test.serial('Throw error if "NPM_TOKEN" is missing', async (t) => { t.is(error.code, 'ENONPMTOKEN'); }); +test.serial('Throw error if "NPM_EMAIL" is missing when used with "NPM_CONFIG__AUTH"', async (t) => { + process.env.HOME = tempy.directory(); + const cwd = tempy.directory(); + process.chdir(cwd); + const npmrc = tempy.file({name: '.npmrc'}); + const env = {NPM_CONFIG__AUTH: 'npm_config__auth'}; + + const [error] = await t.throwsAsync( + require('../lib/set-npmrc-auth')(npmrc, 'http://custom.registry.com', {cwd, env, logger: t.context.logger}) + ); + + t.is(error.name, 'SemanticReleaseError'); + t.is(error.message, 'No npm token specified.'); + t.is(error.code, 'ENONPMTOKEN'); +}); + test.serial('Emulate npm config resolution if "NPM_CONFIG_USERCONFIG" is set', async (t) => { process.env.HOME = tempy.directory(); const cwd = tempy.directory();