diff --git a/lib/utils/error-message.js b/lib/utils/error-message.js index 55c54634542fa..bf5d65c0df3ca 100644 --- a/lib/utils/error-message.js +++ b/lib/utils/error-message.js @@ -154,10 +154,12 @@ function errorMessage (er) { var msg = er.message.replace(/^404\s+/, '') short.push(['404', msg]) if (er.pkgid && er.pkgid !== '-') { + var pkg = er.pkgid.replace(/(?!^)@.*$/, '') + detail.push(['404', '']) detail.push(['404', '', "'" + er.pkgid + "' is not in the npm registry."]) - var valResult = nameValidator(er.pkgid) + var valResult = nameValidator(pkg) if (valResult.validForNewPackages) { detail.push(['404', 'You should bug the author to publish it (or use the name yourself!)']) diff --git a/test/tap/404.js b/test/tap/404.js new file mode 100644 index 0000000000000..710780ad26e60 --- /dev/null +++ b/test/tap/404.js @@ -0,0 +1,72 @@ +'use strict' +const path = require('path') +const test = require('tap').test +const Tacks = require('tacks') +const File = Tacks.File +const Dir = Tacks.Dir +const common = require('../common-tap.js') + +const e404 = /test-npm-404@latest' is not in the npm registry/ +const invalidPackage = /Your package name is not valid, because[\s\S]+1\. name can only contain URL-friendly characters/ + +const basedir = path.join(__dirname, path.basename(__filename, '.js')) +const testdir = path.join(basedir, 'testdir') +const cachedir = path.join(basedir, 'cache') +const globaldir = path.join(basedir, 'global') +const tmpdir = path.join(basedir, 'tmp') + +const env = common.newEnv().extend({ + npm_config_cache: cachedir, + npm_config_tmp: tmpdir, + npm_config_prefix: globaldir, + npm_config_registry: common.registry, + npm_config_loglevel: 'error' +}) + +const fixture = new Tacks(Dir({ + cache: Dir(), + global: Dir(), + tmp: Dir(), + testdir: Dir({ + 'package.json': File({ + name: 'test', + version: '1.0.0' + }) + }) +})) + +function setup () { + cleanup() + fixture.create(basedir) +} + +function cleanup () { + fixture.remove(basedir) +} + +test('setup', function (t) { + setup() + return common.fakeRegistry.listen() +}) + +test('404 message for basic package', function (t) { + return common.npm(['install', 'test-npm-404'], {cwd: testdir, env}).then(([code, stdout, stderr]) => { + t.is(code, 1, 'error code') + t.match(stderr, e404, 'error output') + t.notMatch(stderr, invalidPackage, 'no invalidity error') + }) +}) + +test('404 message for scoped package', function (t) { + return common.npm(['install', '@npm/test-npm-404'], {cwd: testdir, env}).then(([code, stdout, stderr]) => { + t.is(code, 1, 'error code') + t.match(stderr, e404, 'error output') + t.notMatch(stderr, invalidPackage, 'no invalidity error') + }) +}) + +test('cleanup', function (t) { + common.fakeRegistry.close() + cleanup() + t.done() +})