@keg-hub/args-parse
Advanced tools
Comparing version 6.3.2 to 7.0.0
{ | ||
"name": "@keg-hub/args-parse", | ||
"version": "6.3.2", | ||
"version": "7.0.0", | ||
"description": "Parse command line arguments", | ||
"main": "src/index.js", | ||
"repository": { | ||
"url": "git+https://github.com/lancetipton/keg-hub.git", | ||
"url": "git+https://github.com/KegHub/keg-hub.git", | ||
"type": "git" | ||
}, | ||
"bugs": { | ||
"url": "https://github.com/lancetipton/keg-hub/issues" | ||
"url": "https://github.com/KegHub/keg-hub/issues" | ||
}, | ||
"homepage": "https://github.com/lancetipton/keg-hub#readme", | ||
"author": "lancetipton <lancetipton04@gmail.com>", | ||
"homepage": "https://github.com/KegHub/keg-hub#readme", | ||
"author": "KegHub <KegHub@gmail.com>", | ||
"license": "MIT", | ||
@@ -41,4 +41,3 @@ "publishConfig": { | ||
"devDependencies": { | ||
"jest": "26.6.3", | ||
"jest-cli": "26.6.3", | ||
"jest": "27.3.1", | ||
"jest-html-reporter": "3.1.3", | ||
@@ -45,0 +44,0 @@ "rimraf": "3.0.2" |
@@ -10,7 +10,7 @@ # argsParse | ||
```js | ||
"argsParse": "git+https://github.com/lancetipton/argsParse.git" | ||
"argsParse": "git+https://github.com/KegHub/argsParse.git" | ||
``` | ||
### Use It | ||
See test [examples](https://github.com/lancetipton/argsParse/blob/master/__tests__/argsParse.js) | ||
See test [examples](https://github.com/KegHub/argsParse/blob/master/__tests__/argsParse.js) | ||
@@ -57,4 +57,4 @@ ```js | ||
* Path should be relative to the applications root directory | ||
* See default [config](https://github.com/lancetipton/argsParse/blob/master/configs/parse.config.js) | ||
* See default [config](https://github.com/KegHub/argsParse/blob/master/configs/parse.config.js) | ||
* Custom Configs should match the keys within the default config | ||
* `bools` && `environment` |
@@ -111,2 +111,30 @@ module.exports = { | ||
}, | ||
testTask6: { | ||
name: 'testTask6', | ||
options: { | ||
foo: { | ||
description: "Gets the values from TEST_ENV_VALUE env is not set", | ||
env: 'TEST_FOO_ENV_VALUE', | ||
required: true, | ||
}, | ||
bar: { | ||
description: "Gets the boolean values from TEST_ENV_BOOL env if not set", | ||
type: 'bool', | ||
env: 'TEST_BAR_ENV_BOOL' | ||
}, | ||
arr: { | ||
description: "defaults to [1, 2, 'buckle my shoe'] if TEST_ENV_ARR env is not set", | ||
type: 'array', | ||
env: 'TEST_ARR_ENV_ARR', | ||
default: [1, 2, 'buckle my shoe'] | ||
}, | ||
num: { | ||
description: "defaults to 100 if TEST_ENV_NUM env is not set", | ||
type: 'number', | ||
env: 'TEST_NUM_ENV_NUM', | ||
default: 1000 | ||
}, | ||
} | ||
}, | ||
} |
@@ -1,2 +0,10 @@ | ||
const { testTask1, testTask2, testTask3, testTask4, testTask5 } = require('../__mocks__/testTasks') | ||
const { | ||
testTask1, | ||
testTask2, | ||
testTask3, | ||
testTask4, | ||
testTask5, | ||
testTask6, | ||
} = require('../__mocks__/testTasks') | ||
const Ask = require('../__mocks__/ask') | ||
@@ -11,284 +19,374 @@ jest.setMock('@keg-hub/ask-it', Ask) | ||
it('should return an object with the arguments parsed', async () => { | ||
describe('parse passed in args array', () => { | ||
const parsed = await argsParse({ | ||
args: [ 'foo=test', 'doo=f' ], | ||
task: testTask1, | ||
it('should return an object with the arguments parsed', async () => { | ||
const parsed = await argsParse({ | ||
args: [ 'foo=test', 'doo=f' ], | ||
task: testTask1, | ||
}) | ||
expect(parsed.foo).toBe('test') | ||
expect(parsed.doo).toBe(false) | ||
}) | ||
expect(parsed.foo).toBe('test') | ||
expect(parsed.doo).toBe(false) | ||
it('should not parse value matching the next key as the key', async () => { | ||
const parsed = await argsParse({ | ||
args: [ '--context', 'tap', '--tap', 'test' ], | ||
task: testTask2, | ||
}) | ||
expect(parsed.context).toBe('tap') | ||
expect(parsed.tap).toBe('test') | ||
const parsed2 = await argsParse({ | ||
args: [ '-c', 'tap', '-t', 'test' ], | ||
task: testTask2, | ||
}) | ||
expect(parsed2.context).toBe('tap') | ||
expect(parsed2.tap).toBe('test') | ||
}) | ||
it('should call process.exit when a required argument is not passed', async () => { | ||
const orgError = console.error | ||
console.error = jest.fn() | ||
const orgExit = process.exit | ||
process.exit = jest.fn() | ||
const parsed = await argsParse({ | ||
args: [ 'foo=test' ], | ||
task: testTask1, | ||
}) | ||
expect(process.exit).toHaveBeenCalled() | ||
console.error = orgError | ||
process.exit = orgExit | ||
}) | ||
}) | ||
it('should not parse value matching the next key as the key', async () => { | ||
const parsed = await argsParse({ | ||
args: [ '--context', 'tap', '--tap', 'test' ], | ||
task: testTask2, | ||
it('should not parse non-defined task options', async () => { | ||
const parsed = await argsParse({ | ||
args: [ 'doo=test', 'not=defined' ], | ||
task: testTask1, | ||
}) | ||
expect(parsed.not).toBe(undefined) | ||
}) | ||
it('should parse args with -- or =', async () => { | ||
const parsed = await argsParse({ | ||
args: [ 'doo=test', '--foo', 'doot' ], | ||
task: testTask1, | ||
}) | ||
expect(parsed.doo).toBe('test') | ||
expect(parsed.foo).toBe('doot') | ||
}) | ||
expect(parsed.context).toBe('tap') | ||
expect(parsed.tap).toBe('test') | ||
it('should not parse single "-" for full option keys', async () => { | ||
const parsed2 = await argsParse({ | ||
args: [ '-c', 'tap', '-t', 'test' ], | ||
task: testTask2, | ||
const parsed = await argsParse({ | ||
args: [ 'doo=test', '-foo', 'doot' ], | ||
task: testTask1, | ||
}) | ||
expect(parsed.doo).toBe('test') | ||
expect(parsed.foo).toBe('bar') | ||
}) | ||
expect(parsed2.context).toBe('tap') | ||
expect(parsed2.tap).toBe('test') | ||
}) | ||
it('should call process.exit when a required argument is not passed', async () => { | ||
describe('parse special edge-cases', () => { | ||
const orgError = console.error | ||
console.error = jest.fn() | ||
it('should set the first arg to the first option if no other args are passed', async () => { | ||
const parsed = await argsParse({ | ||
args: [ 'auto-set' ], | ||
task: testTask1, | ||
}) | ||
expect(parsed.doo).toBe('auto-set') | ||
}) | ||
const orgExit = process.exit | ||
process.exit = jest.fn() | ||
it('should convert the value type when the type field is set', async () => { | ||
const parsed = await argsParse({ | ||
args: [ 'foo=test' ], | ||
task: testTask1, | ||
const testObj = JSON.stringify({ | ||
test: 'object' | ||
}) | ||
const testArr = JSON.stringify([ 'foo', 'bar' ]) | ||
const parsed = await argsParse({ | ||
args: [ | ||
`number=5`, | ||
`num=0`, | ||
`object=${ testObj }`, | ||
`--obj`, | ||
`${ testObj }`, | ||
`array=${ testArr }`, | ||
`arr=1,2,3`, | ||
`--boolean`, | ||
'true', | ||
`bool=false`, | ||
`--quoted`, | ||
`"Quoted`, | ||
`string"` | ||
], | ||
task: testTask3, | ||
}) | ||
expect(parsed.number).toBe(5) | ||
expect(parsed.num).toBe(0) | ||
expect(typeof parsed.object).toBe('object') | ||
expect(parsed.object.test).toBe('object') | ||
expect(typeof parsed.obj).toBe('object') | ||
expect(parsed.obj.test).toBe('object') | ||
expect(Array.isArray(parsed.array)).toBe(true) | ||
expect(parsed.array[0]).toBe('foo') | ||
expect(parsed.array[1]).toBe('bar') | ||
expect(Array.isArray(parsed.arr)).toBe(true) | ||
expect(parsed.arr[0]).toBe('1') | ||
expect(parsed.arr[1]).toBe('2') | ||
expect(parsed.arr[2]).toBe('3') | ||
expect(parsed.boolean).toBe(true) | ||
expect(parsed.bool).toBe(false) | ||
expect(parsed.quoted).toBe('Quoted string') | ||
}) | ||
expect(process.exit).toHaveBeenCalled() | ||
console.error = orgError | ||
process.exit = orgExit | ||
}) | ||
it('should set the first arg to the first option if no other args are passed', async () => { | ||
const parsed = await argsParse({ | ||
args: [ 'auto-set' ], | ||
task: testTask1, | ||
it('should call @keg-hub/ask-it when no value is passed and task.ask is exist', async () => { | ||
expect(Ask.ask).not.toHaveBeenCalled() | ||
expect(Ask.buildModel).not.toHaveBeenCalled() | ||
const parsed = await argsParse({ | ||
args: [ '--context', 'tap' ], | ||
task: testTask2, | ||
}) | ||
expect(Ask.ask).toHaveBeenCalled() | ||
expect(Ask.buildModel).toHaveBeenCalled() | ||
}) | ||
expect(parsed.doo).toBe('auto-set') | ||
}) | ||
it('should set the default value for an option if no arg is passed', async () => { | ||
const parsed = await argsParse({ | ||
args: [ 'doo=test' ], | ||
task: testTask1, | ||
it('should map the options to the keys when no identifiers are used', async () => { | ||
const parsed = await argsParse({ | ||
args: [ 'test', 'try', 'duper' ], | ||
task: testTask1, | ||
}) | ||
expect(parsed.doo).toBe('test') | ||
expect(parsed.foo).toBe('try') | ||
expect(parsed.baz).toBe('duper') | ||
expect(parsed.env).toBe('development') | ||
}) | ||
expect(parsed.foo).toBe('bar') | ||
it('should parse quoted string values', async () => { | ||
}) | ||
it('should not parse non-defined task options', async () => { | ||
const parsed = await argsParse({ | ||
args: [ 'doo=test', 'not=defined' ], | ||
task: testTask1, | ||
const parsed = await argsParse({ | ||
args: [ '-d', "\"I am a long quoted string value\"", '--foo', '\'single quotes\'' ], | ||
task: testTask1, | ||
}) | ||
expect(parsed.doo).toBe("I am a long quoted string value") | ||
expect(parsed.foo).toBe("single quotes") | ||
}) | ||
expect(parsed.not).toBe(undefined) | ||
}) | ||
it('should parse args with -- or =', async () => { | ||
const parsed = await argsParse({ | ||
args: [ 'doo=test', '--foo', 'doot' ], | ||
task: testTask1, | ||
it('should parse alias, and set the value to the original option key', async () => { | ||
const parsed = await argsParse({ | ||
args: [ 'd=test', 'zoo=alias' ], | ||
task: testTask1, | ||
}) | ||
expect(parsed.foo).toBe('alias') | ||
expect(parsed.zoo).toBe(undefined) | ||
}) | ||
expect(parsed.doo).toBe('test') | ||
expect(parsed.foo).toBe('doot') | ||
}) | ||
it('should not parse single - for full option keys', async () => { | ||
const parsed = await argsParse({ | ||
args: [ 'doo=test', '-foo', 'doot' ], | ||
task: testTask1, | ||
it('should convert --no-* arguments to false value', async () => { | ||
const parsed = await argsParse({ | ||
args: [ '--no-foo', '--bar' ], | ||
task: testTask5, | ||
}) | ||
expect(parsed.foo).toBe(false) | ||
expect(parsed.bar).toBe(true) | ||
}) | ||
expect(parsed.doo).toBe('test') | ||
expect(parsed.foo).toBe('bar') | ||
}) | ||
it('should use the first char as the short name of an option key', async () => { | ||
const parsed = await argsParse({ | ||
args: [ '-d', 'test', '-f', 'doot' ], | ||
task: testTask1, | ||
describe('parse short name version of args', () => { | ||
it('should use the first char as the short name of an option key', async () => { | ||
const parsed = await argsParse({ | ||
args: [ '-d', 'test', '-f', 'doot' ], | ||
task: testTask1, | ||
}) | ||
expect(parsed.doo).toBe('test') | ||
expect(parsed.foo).toBe('doot') | ||
}) | ||
expect(parsed.doo).toBe('test') | ||
expect(parsed.foo).toBe('doot') | ||
it('should allow using the short name with =', async () => { | ||
const parsed = await argsParse({ | ||
args: [ 'd=test' ], | ||
task: testTask1, | ||
}) | ||
expect(parsed.doo).toBe('test') | ||
expect(parsed.d).toBe(undefined) | ||
}) | ||
}) | ||
it('should allow using the short name with =', async () => { | ||
describe('parse default args', () => { | ||
const parsed = await argsParse({ | ||
args: [ 'd=test' ], | ||
task: testTask1, | ||
it('should set the default value for an option if no arg is passed', async () => { | ||
const parsed = await argsParse({ | ||
args: [ 'doo=test' ], | ||
task: testTask1, | ||
}) | ||
expect(parsed.foo).toBe('bar') | ||
}) | ||
expect(parsed.doo).toBe('test') | ||
expect(parsed.d).toBe(undefined) | ||
}) | ||
it('should parse quoted string values', async () => { | ||
const parsed = await argsParse({ | ||
args: [ '-d', "\"I am a long quoted string value\"", '--foo', '\'single quotes\'' ], | ||
task: testTask1, | ||
it('should allow passing an env argument always', async () => { | ||
const parsed = await argsParse({ | ||
args: [ 'd=test', '--env', 'dev' ], | ||
task: testTask1, | ||
}) | ||
expect(parsed.env).toBe('development') | ||
}) | ||
expect(parsed.doo).toBe("I am a long quoted string value") | ||
expect(parsed.foo).toBe("single quotes") | ||
it(`should use default when no option is passed and type and default exist`, async () => { | ||
}) | ||
it('should parse alias, and set the value to the original option key', async () => { | ||
const parsed = await argsParse({ | ||
args: [ 'd=test', 'zoo=alias' ], | ||
task: testTask1, | ||
const parsed = await argsParse({ | ||
args: [], | ||
task: testTask5, | ||
}) | ||
expect(parsed.foo).toBe(testTask5.options.foo.default) | ||
expect(parsed.bar).toBe(testTask5.options.bar.default) | ||
expect(parsed.str).toBe(testTask5.options.str.default) | ||
expect(parsed.num).toBe(testTask5.options.num.default) | ||
expect(parsed.arr).toEqual(testTask5.options.arr.default) | ||
expect(parsed.obj).toEqual(testTask5.options.obj.default) | ||
}) | ||
expect(parsed.foo).toBe('alias') | ||
expect(parsed.zoo).toBe(undefined) | ||
it('should return only the default options when task has no options', async () => { | ||
}) | ||
it('should convert --no-* arguments to false value', async () => { | ||
const parsed = await argsParse({ | ||
args: [ '--no-foo', '--bar' ], | ||
task: testTask5, | ||
const parsed = await argsParse({ | ||
args: [], | ||
task: testTask4, | ||
}) | ||
expect(Object.keys(parsed).length).toBe(1) | ||
expect(Boolean(parsed.env)).toBe(true) | ||
}) | ||
expect(parsed.foo).toBe(false) | ||
expect(parsed.bar).toBe(true) | ||
}) | ||
it('should allow passing an env argument always', async () => { | ||
describe(`Use metadata.env to get values from process.env `, () => { | ||
const parsed = await argsParse({ | ||
args: [ 'd=test', '--env', 'dev' ], | ||
task: testTask1, | ||
afterEach(() => { | ||
delete process.env.TEST_FOO_ENV_VALUE | ||
delete process.env.TEST_BAR_ENV_BOOL | ||
delete process.env.TEST_ARR_ENV_ARR | ||
delete process.env.TEST_NUM_ENV_NUM | ||
}) | ||
expect(parsed.env).toBe('development') | ||
}) | ||
it('should convert the value type when the type field is set', async () => { | ||
const testObj = JSON.stringify({ | ||
test: 'object' | ||
it('should use get the value from the env when the metadata exists as the correct type', async () => { | ||
process.env.TEST_FOO_ENV_VALUE = `foo-value` | ||
process.env.TEST_BAR_ENV_BOOL = 'yes' | ||
process.env.TEST_ARR_ENV_ARR = '1,2,3,4' | ||
process.env.TEST_NUM_ENV_NUM = `1000` | ||
const parsed = await argsParse({ | ||
args: [], | ||
task: testTask6, | ||
}) | ||
expect(parsed.foo).toBe(`foo-value`) | ||
expect(parsed.bar).toBe(true) | ||
expect(parsed.arr).toEqual(['1','2','3','4']) | ||
expect(parsed.num).toBe(1000) | ||
}) | ||
const testArr = JSON.stringify([ 'foo', 'bar' ]) | ||
it('should not use the env when it does not exist', async () => { | ||
process.env.TEST_FOO_ENV_VALUE = `foo-value` | ||
const parsed = await argsParse({ | ||
args: [ | ||
`number=5`, | ||
`num=0`, | ||
`object=${ testObj }`, | ||
`--obj`, | ||
`${ testObj }`, | ||
`array=${ testArr }`, | ||
`arr=1,2,3`, | ||
`--boolean`, | ||
'true', | ||
`bool=false`, | ||
`--quoted`, | ||
`"Quoted`, | ||
`string"` | ||
], | ||
task: testTask3, | ||
expect(process.env.TEST_BAR_ENV_BOOL).toBe(undefined) | ||
const parsed = await argsParse({ | ||
args: [], | ||
task: testTask6, | ||
}) | ||
expect(parsed.foo).toBe(`foo-value`) | ||
expect(parsed.bar).toBe(undefined) | ||
}) | ||
expect(parsed.number).toBe(5) | ||
expect(parsed.num).toBe(0) | ||
expect(typeof parsed.object).toBe('object') | ||
expect(parsed.object.test).toBe('object') | ||
expect(typeof parsed.obj).toBe('object') | ||
expect(parsed.obj.test).toBe('object') | ||
expect(Array.isArray(parsed.array)).toBe(true) | ||
expect(parsed.array[0]).toBe('foo') | ||
expect(parsed.array[1]).toBe('bar') | ||
expect(Array.isArray(parsed.arr)).toBe(true) | ||
expect(parsed.arr[0]).toBe('1') | ||
expect(parsed.arr[1]).toBe('2') | ||
expect(parsed.arr[2]).toBe('3') | ||
expect(parsed.boolean).toBe(true) | ||
expect(parsed.bool).toBe(false) | ||
expect(parsed.quoted).toBe('Quoted string') | ||
it('should use the passed in arg over the env if both are set', async () => { | ||
process.env.TEST_FOO_ENV_VALUE = `foo-value` | ||
}) | ||
it(`should use default when no option is passed and type and default exist`, async () => { | ||
const parsed = await argsParse({ | ||
args: [], | ||
task: testTask5, | ||
const parsed = await argsParse({ | ||
args: [`foo=override-value`], | ||
task: testTask6, | ||
}) | ||
expect(parsed.foo).toBe(`override-value`) | ||
}) | ||
expect(parsed.foo).toBe(testTask5.options.foo.default) | ||
expect(parsed.bar).toBe(testTask5.options.bar.default) | ||
expect(parsed.str).toBe(testTask5.options.str.default) | ||
expect(parsed.num).toBe(testTask5.options.num.default) | ||
expect(parsed.arr).toEqual(testTask5.options.arr.default) | ||
expect(parsed.obj).toEqual(testTask5.options.obj.default) | ||
it('should use the env over a default value', async () => { | ||
process.env.TEST_FOO_ENV_VALUE = `foo-value` | ||
process.env.TEST_NUM_ENV_NUM = `341` | ||
}) | ||
it('should call @keg-hub/ask-it when no value is passed and task.ask is exist', async () => { | ||
expect(Ask.ask).not.toHaveBeenCalled() | ||
expect(Ask.buildModel).not.toHaveBeenCalled() | ||
const parsed = await argsParse({ | ||
args: [ '--context', 'tap' ], | ||
task: testTask2, | ||
const parsed = await argsParse({ | ||
args: [], | ||
task: testTask6, | ||
}) | ||
expect(parsed.num).toBe(341) | ||
}) | ||
expect(Ask.ask).toHaveBeenCalled() | ||
expect(Ask.buildModel).toHaveBeenCalled() | ||
it('should use the passed in arg when env and default exist', async () => { | ||
process.env.TEST_FOO_ENV_VALUE = `foo-value` | ||
process.env.TEST_NUM_ENV_NUM = `341` | ||
}) | ||
it('should map the options to the keys when no identifiers are used', async () => { | ||
const parsed = await argsParse({ | ||
args: [ 'test', 'try', 'duper' ], | ||
task: testTask1, | ||
const parsed = await argsParse({ | ||
args: [`num=222`], | ||
task: testTask6, | ||
}) | ||
expect(parsed.num).toBe(222) | ||
}) | ||
expect(parsed.doo).toBe('test') | ||
expect(parsed.foo).toBe('try') | ||
expect(parsed.baz).toBe('duper') | ||
expect(parsed.env).toBe('development') | ||
}) | ||
it('should return only the default options when task has no options', async () => { | ||
const parsed = await argsParse({ | ||
args: [], | ||
task: testTask4, | ||
}) | ||
expect(Object.keys(parsed).length).toBe(1) | ||
expect(Boolean(parsed.env)).toBe(true) | ||
}) | ||
}) |
@@ -5,2 +5,3 @@ const { checkEnvArg } = require('./checkEnvArg') | ||
const { checkRequired } = require('../utils/checkRequired') | ||
const { checkENVValue } = require('../options/checkENVValue') | ||
const { checkBoolValue } = require('../options/checkBoolValue') | ||
@@ -22,2 +23,6 @@ const { checkValueType } = require('../options/checkValueType') | ||
// Check if meta-data has an env set | ||
// If no value exists, then use the ENV value (process.env.<SOME_ENV>) | ||
args[key] = checkENVValue(args[key], meta.env) | ||
// Ensure any boolean shortcuts are mapped to true or false | ||
@@ -24,0 +29,0 @@ // Allows for using shortcuts like 'yes' or 'no' for 'true' and 'false' |
@@ -12,2 +12,3 @@ const { findArg } = require('./args/findArg') | ||
const { convertNoArgs } = require('./utils/convertNoArgs') | ||
/** | ||
@@ -95,3 +96,3 @@ * Loops the task options looking to a match in the passed in options array | ||
// Get all the name of the options for the task | ||
// Get all the names of the options for the task | ||
// This is used later to compare the keys with the passed in options | ||
@@ -98,0 +99,0 @@ const taskKeys = isObj(task.options) && Object.keys(task.options) |
@@ -11,6 +11,7 @@ const { getConfig } = require('../utils/getConfig') | ||
const { defaultArgs } = getConfig() | ||
if(!defaultArgs || options.env) return options | ||
if(!defaultArgs) return options | ||
return Object.entries(defaultArgs) | ||
.reduce((updated, [ name, meta ]) => { | ||
// Only set the default option, if it does not already exist | ||
if(!updated[name]) updated[name] = meta | ||
@@ -17,0 +18,0 @@ |
@@ -33,2 +33,3 @@ const { getConfig } = require('../utils/getConfig') | ||
const checkBoolValue = value => { | ||
if(!exists(value) || isBool(value)) return value | ||
@@ -40,7 +41,10 @@ | ||
// Check the value is one of the joined bool options | ||
return boolOpts.all.indexOf(lowerVal) === -1 | ||
return !boolOpts.all.includes(lowerVal) | ||
? value | ||
: boolOpts.truthy.indexOf(lowerVal) !== -1 | ||
: boolOpts.truthy.includes(lowerVal) | ||
? true | ||
: false | ||
// Should not be needed, but adding incase I missed an edge case some how | ||
: boolOpts.falsy.includes(lowerVal) | ||
? false | ||
: value | ||
} | ||
@@ -47,0 +51,0 @@ |
@@ -104,3 +104,4 @@ const { checkBoolValue } = require('./checkBoolValue') | ||
case 'bool': { | ||
return toBool(checkBoolValue(value)) | ||
const boolVal = checkBoolValue(value) | ||
return exists(boolVal) ? toBool(boolVal) : undefined | ||
} | ||
@@ -107,0 +108,0 @@ default: { |
Environment variable access
Supply chain riskPackage accesses environment variables, which may be a sign of credential stuffing or data theft.
Found 5 instances in 1 package
50578
3
34
1404
24