diff options
author | isaacs <i@izs.me> | 2020-08-18 19:57:38 +0300 |
---|---|---|
committer | Ruy Adorno <ruyadorno@hotmail.com> | 2020-08-20 20:19:38 +0300 |
commit | ea80f35d853c5e17b129f95c869dc2359ed82663 (patch) | |
tree | bf7adf91d27ebddd4a0fa8c26db8a319d8c1599e /test/lib/utils | |
parent | 8872be9cafd2a8dae4df3424b7ae3e4cbc662522 (diff) |
move flat-options.js from lib/config/ to lib/utils/
PR-URL: https://github.com/npm/cli/pull/1688
Credit: @isaacs
Close: #1688
Reviewed-by: @ruyadorno
Diffstat (limited to 'test/lib/utils')
-rw-r--r-- | test/lib/utils/flat-options.js | 329 |
1 files changed, 329 insertions, 0 deletions
diff --git a/test/lib/utils/flat-options.js b/test/lib/utils/flat-options.js new file mode 100644 index 000000000..8ababa982 --- /dev/null +++ b/test/lib/utils/flat-options.js @@ -0,0 +1,329 @@ +const t = require('tap') + +process.env.NODE = '/path/to/some/node' + +const logs = [] +const log = require('npmlog') +log.warn = (...args) => logs.push(['warn', ...args]) +log.verbose = (...args) => logs.push(['verbose', ...args]) + +class Mocknpm { + constructor (opts = {}) { + this.modes = { + exec: 0o777, + file: 0o666, + umask: 0o22 + } + this.color = true + this.projectScope = '@npmcli' + this.tmp = '/tmp' + this.command = 'test' + this.globalPrefix = '/usr/local' + this.localPrefix = '/path/to/npm/cli' + this.prefix = this.localPrefix + this.version = '7.6.5' + this.config = new MockConfig(opts) + this.flatOptions = null + } +} + +class MockConfig { + constructor (opts = {}) { + this.list = [{ + cache: 'cache', + 'node-version': '1.2.3', + global: 'global', + 'metrics-registry': 'metrics-registry', + 'send-metrics': 'send-metrics', + registry: 'registry', + access: 'access', + 'always-auth': 'always-auth', + audit: 'audit', + 'audit-level': 'audit-level', + 'auth-type': 'auth-type', + before: 'before', + browser: 'browser', + ca: 'ca', + cafile: 'cafile', + call: 'call', + cert: 'cert', + key: 'key', + 'cache-lock-retries': 'cache-lock-retries', + 'cache-lock-stale': 'cache-lock-stale', + 'cache-lock-wait': 'cache-lock-wait', + cidr: 'cidr', + 'read-only': 'read-only', + preid: 'preid', + 'tag-version-prefix': 'tag-version-prefix', + 'allow-same-version': 'allow-same-version', + message: 'message', + 'commit-hooks': 'commit-hooks', + 'git-tag-version': 'git-tag-version', + 'sign-git-commit': 'sign-git-commit', + 'sign-git-tag': 'sign-git-tag', + depth: 'depth', + description: 'description', + searchexclude: 'searchexclude', + searchlimit: 'searchlimit', + searchopts: 'searchopts', + searchstaleness: 'searchstaleness', + 'dry-run': 'dry-run', + 'engine-strict': 'engine-strict', + 'fetch-retries': 'fetch-retries', + 'fetch-retry-factor': 'fetch-retry-factor', + 'fetch-retry-mintimeout': 'fetch-retry-mintimeout', + 'fetch-retry-maxtimeout': 'fetch-retry-maxtimeout', + force: 'force', + 'format-package-lock': 'format-package-lock', + fund: 'fund', + git: 'git', + viewer: 'viewer', + editor: 'editor', + 'bin-links': 'bin-links', + 'rebuild-bundle': 'rebuild-bundle', + package: 'package', + 'package-lock': 'package-lock', + 'package-lock-only': 'package-lock-only', + 'global-style': 'global-style', + 'legacy-bundling': 'legacy-bundling', + 'script-shell': 'script-shell', + omit: [], + include: [], + save: 'save', + 'save-bundle': 'save-bundle', + 'save-dev': 'save-dev', + 'save-optional': 'save-optional', + 'save-peer': 'save-peer', + 'save-prod': 'save-prod', + 'save-exact': 'save-exact', + 'save-prefix': 'save-prefix', + otp: 'otp', + offline: 'offline', + 'prefer-online': 'prefer-online', + 'prefer-offline': 'prefer-offline', + 'cache-max': 'cache-max', + 'cache-min': 'cache-min', + 'strict-ssl': 'strict-ssl', + tag: 'tag', + 'user-agent': 'user-agent', + '@scope:registry': '@scope:registry', + '//nerf.dart:_authToken': '//nerf.dart:_authToken', + ...opts + }] + } + get (key) { + return this.list[0][key] + } + set (key, val) { + this.list[0][key] = val + } +} + +const flatOptions = require('../../../lib/utils/flat-options.js') +t.match(logs, [[ + 'verbose', + 'npm-session', + /^[0-9a-f]{16}$/ +]], 'logged npm session verbosely') +logs.length = 0 + +t.test('basic', t => { + const npm = new Mocknpm() + const generatedFlat = flatOptions(npm) + const clean = { + ...generatedFlat, + npmBin: '/path/to/npm/bin.js', + log: {}, + npmSession: '12345', + cache: generatedFlat.cache.replace(/\\/g, '/') + } + t.matchSnapshot(clean, 'flat options') + t.equal(generatedFlat.npmBin, require.main.filename) + // test the object is frozen + generatedFlat.newField = 'asdf' + t.equal(generatedFlat.newField, undefined, 'object is frozen') + const preExistingOpts = { flat: 'options' } + npm.flatOptions = preExistingOpts + t.equal(flatOptions(npm), preExistingOpts, 'use pre-existing npm.flatOptions') + t.end() +}) + +t.test('get preferOffline from cache-min', t => { + const npm = new Mocknpm({ + 'cache-min': 9999999, + 'prefer-offline': undefined + }) + const opts = flatOptions(npm) + t.equal(opts.preferOffline, true, 'got preferOffline from cache min') + logs.length = 0 + t.equal(opts.cacheMin, 9999999, 'opts.cacheMin is set') + t.match(logs, []) + logs.length = 0 + t.end() +}) + +t.test('get preferOnline from cache-max', t => { + const npm = new Mocknpm({ + 'cache-max': -1, + 'prefer-online': undefined + }) + const opts = flatOptions(npm) + t.equal(opts.preferOnline, true, 'got preferOnline from cache min') + logs.length = 0 + t.equal(opts.cacheMax, -1, 'opts.cacheMax is set') + t.match(logs, []) + logs.length = 0 + t.end() +}) + +t.test('tag emits warning', t => { + const npm = new Mocknpm({ tag: 'foobar' }) + t.equal(flatOptions(npm).tag, 'foobar', 'tag is foobar') + t.match(logs, []) + logs.length = 0 + t.end() +}) + +t.test('scope emits warning', t => { + const npm = new Mocknpm() + logs.length = 0 + t.equal(flatOptions(npm).scope, '@npmcli') + t.match(logs, []) + logs.length = 0 + t.end() +}) + +t.test('omit/include options', t => { + t.test('omit explicitly', t => { + const npm = new Mocknpm({ + omit: ['dev', 'optional', 'peer'] + }) + t.strictSame(flatOptions(npm).omit, ['dev', 'optional', 'peer']) + t.end() + }) + + t.test('omit and include some', t => { + const npm = new Mocknpm({ + omit: ['dev', 'optional', 'peer'], + include: ['peer'] + }) + t.strictSame(flatOptions(npm).omit, ['dev', 'optional']) + t.end() + }) + + t.test('dev flag', t => { + const npm = new Mocknpm({ + omit: ['dev', 'optional', 'peer'], + include: [], + dev: true + }) + t.strictSame(flatOptions(npm).omit, ['optional', 'peer']) + t.end() + }) + + t.test('production flag', t => { + const npm = new Mocknpm({ + omit: [], + include: [], + production: true + }) + t.strictSame(flatOptions(npm).omit, ['dev']) + t.end() + }) + + t.test('only', t => { + const cases = ['prod', 'production'] + t.plan(cases.length) + cases.forEach(c => t.test(c, t => { + const npm = new Mocknpm({ + omit: [], + include: [], + only: c + }) + t.strictSame(flatOptions(npm).omit, ['dev']) + t.end() + })) + }) + + t.test('also dev', t => { + const npm = new Mocknpm({ + omit: ['dev', 'optional', 'peer'], + also: 'dev' + }) + t.strictSame(flatOptions(npm).omit, ['optional', 'peer']) + t.end() + }) + + t.test('no-optional', t => { + const npm = new Mocknpm({ + optional: false, + omit: null, + include: null + }) + t.strictSame(flatOptions(npm).omit, ['optional']) + t.end() + }) + + t.end() +}) + +t.test('get the node without the environ', t => { + delete process.env.NODE + t.equal(flatOptions(new Mocknpm()).nodeBin, process.execPath) + t.end() +}) + +t.test('various default values and falsey fallbacks', t => { + const npm = new Mocknpm({ + 'script-shell': false, + registry: 'http://example.com', + 'metrics-registry': null, + 'searchlimit': 0, + 'save-exact': false, + 'save-prefix': '>=' + }) + const opts = flatOptions(npm) + t.equal(opts.scriptShell, undefined, 'scriptShell is undefined if falsey') + t.equal(opts.metricsRegistry, 'http://example.com', + 'metricsRegistry defaults to registry') + t.equal(opts.search.limit, 20, 'searchLimit defaults to 20') + t.equal(opts.savePrefix, '>=', 'save-prefix respected if no save-exact') + logs.length = 0 + t.end() +}) + +t.test('save-type', t => { + const base = { + 'save-optional': false, + 'save-peer': false, + 'save-dev': false, + 'save-prod': false + } + const cases = [ + ['peerOptional', { + 'save-optional': true, + 'save-peer': true, + }], + ['optional', { + 'save-optional': true + }], + ['dev', { + 'save-dev': true + }], + ['peer', { + 'save-peer': true + }], + ['prod', { + 'save-prod': true + }], + [null, {}] + ] + for (const [expect, options] of cases) { + const opts = flatOptions(new Mocknpm({ + ...base, + ...options + })) + t.equal(opts.saveType, expect, JSON.stringify(options)) + } + t.end() +}) |