diff --git a/.travis.yml b/.travis.yml index ff7ce77..84bbe74 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,5 +1,6 @@ language: node_js node_js: + - "14" - "12" - "10" - "8" diff --git a/CHANGELOG.md b/CHANGELOG.md index 4c72b18..888d0ad 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,9 @@ # Changelog +## 2.9.0 - 2020.09.30 +- Missing values in schema now default to empty strings for `errorOnRegex` (thanks @FokkeZB) +- Minor modernization and refactoring of unit tests + ## 2.8.0 - 2020.03.25 - Update dependencies while retaining compatibility with Node 6 - Add ability to configure through environment variables (thanks @Levino) diff --git a/package-lock.json b/package-lock.json index e64aafd..33faadf 100644 --- a/package-lock.json +++ b/package-lock.json @@ -36,12 +36,6 @@ "pkg-up": "^3.1.0" } }, - "caniuse-lite": { - "version": "1.0.30001037", - "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001037.tgz", - "integrity": "sha512-qQP40FzWQ1i9RTjxppOUnpM8OwTBFL5DQbjoR9Az32EtM7YUZOw9orFO6rj1C+xWAGzz+X3bUe09Jf5Ep+zpuA==", - "dev": true - }, "electron-to-chromium": { "version": "1.3.384", "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.384.tgz", @@ -377,12 +371,6 @@ "pkg-up": "^3.1.0" } }, - "caniuse-lite": { - "version": "1.0.30001037", - "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001037.tgz", - "integrity": "sha512-qQP40FzWQ1i9RTjxppOUnpM8OwTBFL5DQbjoR9Az32EtM7YUZOw9orFO6rj1C+xWAGzz+X3bUe09Jf5Ep+zpuA==", - "dev": true - }, "electron-to-chromium": { "version": "1.3.384", "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.384.tgz", @@ -2771,12 +2759,6 @@ "pkg-up": "^3.1.0" } }, - "caniuse-lite": { - "version": "1.0.30001037", - "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001037.tgz", - "integrity": "sha512-qQP40FzWQ1i9RTjxppOUnpM8OwTBFL5DQbjoR9Az32EtM7YUZOw9orFO6rj1C+xWAGzz+X3bUe09Jf5Ep+zpuA==", - "dev": true - }, "electron-to-chromium": { "version": "1.3.384", "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.384.tgz", @@ -3012,6 +2994,31 @@ "integrity": "sha512-JNbGaHFCLwgHn/iCckiGSOZ1XYHsKFwREtzPwSGCVld1SGhOlmZw2D4ZI94HQCrBHbADzW9m4LER/8olJTRGHA==", "dev": true }, + "@types/sinon": { + "version": "9.0.7", + "resolved": "https://registry.npmjs.org/@types/sinon/-/sinon-9.0.7.tgz", + "integrity": "sha512-uyFiy2gp4P/FK9pmU3WIbT5ZzH54hCswwRkQFhxX7xl8jzhW3g+xOkVqk5YP4cIO//Few8UDAX0MtzFpqBEqwA==", + "dev": true, + "requires": { + "@types/sinonjs__fake-timers": "*" + } + }, + "@types/sinon-chai": { + "version": "3.2.5", + "resolved": "https://registry.npmjs.org/@types/sinon-chai/-/sinon-chai-3.2.5.tgz", + "integrity": "sha512-bKQqIpew7mmIGNRlxW6Zli/QVyc3zikpGzCa797B/tRnD9OtHvZ/ts8sYXV+Ilj9u3QRaUEM8xrjgd1gwm1BpQ==", + "dev": true, + "requires": { + "@types/chai": "*", + "@types/sinon": "*" + } + }, + "@types/sinonjs__fake-timers": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/@types/sinonjs__fake-timers/-/sinonjs__fake-timers-6.0.2.tgz", + "integrity": "sha512-dIPoZ3g5gcx9zZEszaxLSVTvMReD3xxyyDnQUjA6IYDG9Ba2AV0otMPs+77sG9ojB4Qr2N2Vk5RnKeuA0X/0bg==", + "dev": true + }, "acorn": { "version": "6.4.1", "resolved": "https://registry.npmjs.org/acorn/-/acorn-6.4.1.tgz", @@ -3561,6 +3568,12 @@ "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-5.3.1.tgz", "integrity": "sha512-L28STB170nwWS63UjtlEOE3dldQApaJXZkOI1uMFfzf3rRuPegHaHesyee+YxQ+W6SvRDQV6UrdOdRiR153wJg==" }, + "caniuse-lite": { + "version": "1.0.30001140", + "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001140.tgz", + "integrity": "sha512-xFtvBtfGrpjTOxTpjP5F2LmN04/ZGfYV8EQzUIC/RmKpdrmzJrjqlJ4ho7sGuAMPko2/Jl08h7x9uObCfBFaAA==", + "dev": true + }, "caseless": { "version": "0.12.0", "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", @@ -3868,12 +3881,6 @@ "pkg-up": "^3.1.0" } }, - "caniuse-lite": { - "version": "1.0.30001037", - "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001037.tgz", - "integrity": "sha512-qQP40FzWQ1i9RTjxppOUnpM8OwTBFL5DQbjoR9Az32EtM7YUZOw9orFO6rj1C+xWAGzz+X3bUe09Jf5Ep+zpuA==", - "dev": true - }, "electron-to-chromium": { "version": "1.3.384", "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.3.384.tgz", @@ -5931,17 +5938,24 @@ } }, "handlebars": { - "version": "4.4.5", - "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.4.5.tgz", - "integrity": "sha512-0Ce31oWVB7YidkaTq33ZxEbN+UDxMMgThvCe8ptgQViymL5DPis9uLdTA13MiRPhgvqyxIegugrP97iK3JeBHg==", + "version": "4.7.6", + "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.7.6.tgz", + "integrity": "sha512-1f2BACcBfiwAfStCKZNrUCgqNZkGsAT7UM3kkYtXuLo0KnaVfjKOyf7PRzB6++aK9STyT1Pd2ZCPe3EGOXleXA==", "dev": true, "requires": { + "minimist": "^1.2.5", "neo-async": "^2.6.0", - "optimist": "^0.6.1", "source-map": "^0.6.1", - "uglify-js": "^3.1.4" + "uglify-js": "^3.1.4", + "wordwrap": "^1.0.0" }, "dependencies": { + "minimist": { + "version": "1.2.5", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.5.tgz", + "integrity": "sha512-FM9nNUYrRBAELZQT3xeZQ7fmMOBg6nWNmJKTcgsJeaLstP/UODVpGsr5OhXhhXg6f+qtJ8uiZ+PUxkDWcgIXLw==", + "dev": true + }, "source-map": { "version": "0.6.1", "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", @@ -6954,9 +6968,9 @@ } }, "lodash": { - "version": "4.17.15", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.15.tgz", - "integrity": "sha512-8xOcRHvCjnocdS5cpwXQXVzmmh5e5+saE2QGoeQmbKmRS6J3VQppPOIt0MnmE+4xlZoumy0GPG0D0MVIQbNA1A==", + "version": "4.17.19", + "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.19.tgz", + "integrity": "sha512-JNvd8XER9GQX0v2qJgsaN/mzFCNA5BRe/j8JN9d+tWyGLSodKQHKFicdwNYzWwI3wjRnaKPsGj1XkBjx/F96DQ==", "dev": true }, "lodash.flattendeep": { @@ -7960,24 +7974,6 @@ "mimic-fn": "^1.0.0" } }, - "optimist": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/optimist/-/optimist-0.6.1.tgz", - "integrity": "sha1-2j6nRob6IaGaERwybpDrFaAZZoY=", - "dev": true, - "requires": { - "minimist": "~0.0.1", - "wordwrap": "~0.0.2" - }, - "dependencies": { - "wordwrap": { - "version": "0.0.3", - "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-0.0.3.tgz", - "integrity": "sha1-o9XabNXAvAAI03I0u68b7WMFkQc=", - "dev": true - } - } - }, "optionator": { "version": "0.8.2", "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.8.2.tgz", diff --git a/package.json b/package.json index 168fb73..6f4a5cd 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "dotenv-extended", - "version": "2.8.0", + "version": "2.9.0", "description": "A module for loading .env files and optionally loading defaults and a schema for validating all values are present.", "repository": "git@github.com:keithmorris/node-dotenv-extended.git", "main": "lib/index.js", @@ -28,6 +28,8 @@ "@babel/preset-env": "^7.9.0", "@types/chai": "^4.2.11", "@types/mocha": "^7.0.2", + "@types/sinon": "^9.0.0", + "@types/sinon-chai": "^3.2.4", "babel-eslint": "8.2.6", "chai": "^4.2.0", "coveralls": "^3.0.7", diff --git a/src/bin/index.js b/src/bin/index.js index f3a2b1e..dd1cf80 100755 --- a/src/bin/index.js +++ b/src/bin/index.js @@ -7,7 +7,7 @@ */ import {config} from '..'; -import {parseCommand} from '../utils/parse-command'; +import parseCommand from '../utils/parse-command'; import {spawn} from 'cross-spawn'; function loadAndExecute(args) { diff --git a/src/config.js b/src/config.js index acc2e73..150eefe 100644 --- a/src/config.js +++ b/src/config.js @@ -1,11 +1,11 @@ import {config} from './index'; -function reduceArguments(prev, curr) { +const reduceArguments = (prev, curr) => { const matches = curr.match(/^dotenv_config_(.+)=(.+)/); return hasMatches(matches) ? expandKeyValFromMatches(matches, prev) : prev; -} +}; const expandKeyValFromMatches = ([, key, value], prev) => ({ ...prev, diff --git a/src/index.js b/src/index.js index d48bd29..7cc8aec 100644 --- a/src/index.js +++ b/src/index.js @@ -55,7 +55,7 @@ export const config = options => { if (options.errorOnRegex) { const regexMismatchKeys = schemaKeys.filter(function (key) { if (schema[key]) { - return !new RegExp(schema[key]).test(config[key]); + return !new RegExp(schema[key]).test(typeof config[key] === 'string' ? config[key] : ''); } }); diff --git a/test/.env.schema.regex-optional b/test/.env.schema.regex-optional new file mode 100644 index 0000000..51552d1 --- /dev/null +++ b/test/.env.schema.regex-optional @@ -0,0 +1,5 @@ +TEST_VAR=^my test var$ +TEST_ONE=^overridden$ + +TEST_MISSING_OPTIONAL=^(optional)?$ +TEST_MISSING_REQUIRED=^optional$ diff --git a/test/test.spec.js b/test/test.spec.js index 6b158ac..1796187 100644 --- a/test/test.spec.js +++ b/test/test.spec.js @@ -4,10 +4,13 @@ import mockery from 'mockery'; import sinon from 'sinon'; import sinonChai from 'sinon-chai'; +import dotenvex from '../lib/index'; +import parseCommand from '../lib/utils/parse-command'; +import getConfigFromEnv from '../lib/utils/config-from-env'; + chai.use(sinonChai); describe('dotenv-extended tests', () => { - let dotenvex; before(() => { mockery.enable({ @@ -16,7 +19,6 @@ describe('dotenv-extended tests', () => { useCleanCache: true }); sinon.stub(console, 'error'); - dotenvex = require('../'); }); after(() => { @@ -163,6 +165,16 @@ describe('dotenv-extended tests', () => { expect(runTest).to.throw('REGEX MISMATCH: TEST_TWO, TEST_THREE'); }); + it('Should default missing values to empty string when errorOnRegex is true', () => { + const runTest = () => { + dotenvex.load({ + schema: '.env.schema.regex-optional', + errorOnRegex: true, + }); + }; + expect(runTest).to.throw('REGEX MISMATCH: TEST_MISSING_REQUIRED'); + }); + it('Should log an error when silent is set to false and .env.defaults is missing', function () { dotenvex.load({silent: false}); expect(console.error).to.have.been.calledOnce; @@ -183,9 +195,6 @@ describe('Supporting libraries tests', () => { delete process.env.DOTENV_CONFIG_ASSIGN_TO_PROCESS_ENV; delete process.env.DOTENV_CONFIG_OVERRIDE_PROCESS_ENV; }); - - const parseCommand = require('../lib/utils/parse-command').parseCommand; - const getConfigFromEnv = require('../lib/utils/config-from-env').getConfigFromEnv; const cliArgs = [ '--encoding=utf8', '--silent=true',