Socket
Socket
Sign inDemoInstall

dotenv-expand

Package Overview
Dependencies
Maintainers
1
Versions
23
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

dotenv-expand - npm Package Compare versions

Comparing version 10.0.0 to 11.0.0

.github/FUNDING.yml

21

CHANGELOG.md

@@ -5,4 +5,23 @@ # Changelog

## [Unreleased](https://github.com/motdotla/dotenv-expand/compare/v10.0.0...master)
## [Unreleased](https://github.com/motdotla/dotenv-expand/compare/v11.0.0...master)
## [11.0.0](https://github.com/motdotla/dotenv-expand/compare/v10.0.0...v11.0.0) (2024-02-10)
### Added
- Add typings for `import dotenv-expand/config` ([#99](https://github.com/motdotla/dotenv-expand/pull/99))
- Support expansion of dot in env variable names like `POSTGRESQL.BASE.USER` ([#93](https://github.com/motdotla/dotenv-expand/pull/93))
- Add `processEnv` option ([#105](https://github.com/motdotla/dotenv-expand/pull/105))
- Add support for default format of `${VAR-default}` ([#109](https://github.com/motdotla/dotenv-expand/pull/109))
### Changed
- Do not expand prior `process.env` environment variables. NOTE: make sure to see updated README regarding `dotenv.config({ processEnv: {} })` ([#104](https://github.com/motdotla/dotenv-expand/pull/104))
- 🐞 handle `$var1$var2` ([#103](https://github.com/motdotla/dotenv-expand/issues/103), [#104](https://github.com/motdotla/dotenv-expand/pull/104))
- 🐞 fix fatal recursive error when variable defines value with same variable `VAR=$VAR` [#98](https://github.com/motdotla/dotenv-expand/issues/98)
### Removed
- Remove `ignoreProcessEnv` option (use `processEnv` option going forward)
## [10.0.0](https://github.com/motdotla/dotenv-expand/compare/v9.0.0...v10.0.0) (2022-12-16)

@@ -9,0 +28,0 @@

39

lib/main.d.ts
// TypeScript Version: 3.0
/// <reference types="node" />
export interface DotenvPopulateInput {
[name: string]: string;
}
export interface DotenvParseInput {
[name: string]: string;
}
export interface DotenvParseOutput {
[name: string]: string;
}
export interface DotenvExpandOptions {
ignoreProcessEnv?: boolean;
error?: Error;
parsed?: {
[name: string]: string;
}
/**
* Default: `process.env`
*
* Specify an object to write your secrets to. Defaults to process.env environment variables.
*
* example: `const processEnv = {}; require('dotenv').config({ processEnv: processEnv })`
*/
processEnv?: DotenvPopulateInput;
/**
* Default: `object`
*
* Object coming from dotenv's parsed result.
*/
parsed?: DotenvParseInput;
}
export interface DotenvExpandOutput {
ignoreProcessEnv?: boolean;
error?: Error;
parsed?: {
[name: string]: string;
};
parsed?: DotenvParseOutput;
}

@@ -25,3 +46,3 @@

*
* @param options - additional options. example: `{ ignoreProcessEnv: false, error: null, parsed: { { KEY: 'value' } }`
* @param options - additional options. example: `{ processEnv: {}, error: null, parsed: { { KEY: 'value' } }`
* @returns an object with a `parsed` key if successful or `error` key if an error occurred. example: { parsed: { KEY: 'value' } }

@@ -28,0 +49,0 @@ *

'use strict'
// like String.prototype.search but returns the last index
function _searchLast (str, rgx) {
const matches = Array.from(str.matchAll(rgx))
return matches.length > 0 ? matches.slice(-1)[0].index : -1
}
// * /
// * (\\)? # is it escaped with a backslash?
// * (\$) # literal $
// * (?!\() # shouldnt be followed by parenthesis
// * (\{?) # first brace wrap opening
// * ([\w.]+) # key
// * (?::-((?:\$\{(?:\$\{(?:\$\{[^}]*\}|[^}])*}|[^}])*}|[^}])+))? # optional default nested 3 times
// * (\}?) # last brace warp closing
// * /xi
function _interpolate (envValue, environment, config) {
// find the last unescaped dollar sign in the
// value so that we can evaluate it
const lastUnescapedDollarSignIndex = _searchLast(envValue, /(?!(?<=\\))\$/g)
const DOTENV_SUBSTITUTION_REGEX = /(\\)?(\$)(?!\()(\{?)([\w.]+)(?::?-((?:\$\{(?:\$\{(?:\$\{[^}]*\}|[^}])*}|[^}])*}|[^}])+))?(\}?)/gi
// If we couldn't match any unescaped dollar sign
// let's return the string as is
if (lastUnescapedDollarSignIndex === -1) return envValue
function _resolveEscapeSequences (value) {
return value.replace(/\\\$/g, '$')
}
// This is the right-most group of variables in the string
const rightMostGroup = envValue.slice(lastUnescapedDollarSignIndex)
function interpolate (value, processEnv, parsed) {
return value.replace(DOTENV_SUBSTITUTION_REGEX, (match, escaped, dollarSign, openBrace, key, defaultValue, closeBrace) => {
if (escaped === '\\') {
return match.slice(1)
} else {
if (processEnv[key]) {
return processEnv[key]
}
/**
* This finds the inner most variable/group divided
* by variable name and default value (if present)
* (
* (?!(?<=\\))\$ // only match dollar signs that are not escaped
* {? // optional opening curly brace
* ([\w]+) // match the variable name
* (?::-([^}\\]*))? // match an optional default value
* }? // optional closing curly brace
* )
*/
const matchGroup = /((?!(?<=\\))\${?([\w]+)(?::-([^}\\]*))?}?)/
const match = rightMostGroup.match(matchGroup)
if (defaultValue) {
if (defaultValue.startsWith('$')) {
return interpolate(defaultValue, processEnv, parsed)
} else {
return defaultValue
}
}
if (match != null) {
const [, group, variableName, defaultValue] = match
return parsed[key] || ''
}
})
}
return _interpolate(
envValue.replace(
group,
environment[variableName] ||
defaultValue ||
config.parsed[variableName] ||
''
),
environment,
config
)
function expand (options) {
let processEnv = process.env
if (options && options.processEnv != null) {
processEnv = options.processEnv
}
return envValue
}
for (const key in options.parsed) {
let value = options.parsed[key]
function _resolveEscapeSequences (value) {
return value.replace(/\\\$/g, '$')
}
// don't interpolate if it exists already in processEnv
if (Object.prototype.hasOwnProperty.call(processEnv, key)) {
value = processEnv[key]
} else {
value = interpolate(value, processEnv, options.parsed)
}
function expand (config) {
// if ignoring process.env, use a blank object
const environment = config.ignoreProcessEnv ? {} : process.env
for (const configKey in config.parsed) {
const value = Object.prototype.hasOwnProperty.call(environment, configKey)
? environment[configKey]
: config.parsed[configKey]
config.parsed[configKey] = _resolveEscapeSequences(
_interpolate(value, environment, config)
)
options.parsed[key] = _resolveEscapeSequences(value)
}
for (const processKey in config.parsed) {
environment[processKey] = config.parsed[processKey]
for (const processKey in options.parsed) {
processEnv[processKey] = options.parsed[processKey]
}
return config
return options
}
module.exports.expand = expand
{
"name": "dotenv-expand",
"version": "10.0.0",
"version": "11.0.0",
"description": "Expand environment variables using dotenv",

@@ -21,3 +21,5 @@ "main": "lib/main.js",

"pretest": "npm run lint && npm run dts-check",
"test": "lab tests --coverage"
"test": "tap tests/*.js --100 -Rspec",
"prerelease": "npm test",
"release": "standard-version"
},

@@ -39,8 +41,6 @@ "repository": {

"devDependencies": {
"@hapi/lab": "^24.5.1",
"@types/node": "^17.0.8",
"dotenv": "16.0.3",
"lab": "^14.3.4",
"should": "^11.2.1",
"@types/node": "^18.11.3",
"standard": "^16.0.4",
"standard-version": "^9.5.0",
"tap": "^16.3.0",
"typescript": "^4.5.4"

@@ -50,3 +50,6 @@ },

"node": ">=12"
},
"dependencies": {
"dotenv": "^16.4.1"
}
}
<div align="center">
🎉 announcing <a href="https://github.com/dotenvx/dotenvx">dotenvx</a>. <em>run anywhere, multi-environment, encrypted envs</em>.
</div>
&nbsp;
<div align="center">
<p>

@@ -21,19 +27,19 @@ <sup>

<br>
<a href="https://retool.com/?utm_source=sponsor&utm_campaign=dotenv">
<a href="https://workos.com/?utm_campaign=github_repo&utm_medium=referral&utm_content=dotenv&utm_source=github">
<div>
<img src="https://res.cloudinary.com/dotenv-org/image/upload/c_scale,w_300/v1664466968/logo-full-black_vidfqf.png" width="270" alt="Retool">
<img src="https://res.cloudinary.com/dotenv-org/image/upload/c_scale,w_400/v1665605496/68747470733a2f2f73696e647265736f726875732e636f6d2f6173736574732f7468616e6b732f776f726b6f732d6c6f676f2d77686974652d62672e737667_zdmsbu.svg" width="270" alt="WorkOS">
</div>
<b>Retool helps developers build custom internal software, like CRUD apps and admin panels, really fast.</b>
<b>Your App, Enterprise Ready.</b>
<div>
<sup>Build UIs visually with flexible components, connect to any data source, and write business logic in JavaScript.</sup>
<sup>Add Single Sign-On, Multi-Factor Auth, and more, in minutes instead of months.</sup>
</div>
</a>
<br>
<a href="https://workos.com/?utm_campaign=github_repo&utm_medium=referral&utm_content=dotenv&utm_source=github">
<br/>
<a href="https://runalloy.com/?utm_source=github&utm_medium=referral&utm_campaign=1224_dotenv">
<div>
<img src="https://res.cloudinary.com/dotenv-org/image/upload/c_scale,w_400/v1665605496/68747470733a2f2f73696e647265736f726875732e636f6d2f6173736574732f7468616e6b732f776f726b6f732d6c6f676f2d77686974652d62672e737667_zdmsbu.svg" width="270" alt="WorkOS">
<img src="https://res.cloudinary.com/dotenv-org/image/upload/c_crop,g_center,h_65,w_290,x_0,y_0/v1704258787/AlloyAutomation-logo_dqin8c.svg" width="370" alt="Alloy Automation">
</div>
<b>Your App, Enterprise Ready.</b>
<b>Launch user-facing integrations faster</b>
<div>
<sup>Add Single Sign-On, Multi-Factor Auth, and more, in minutes instead of months.</sup>
<sup>Easily spin up hundreds of integrations. Sign up free or read our docs first</sup>
</div>

@@ -90,3 +96,3 @@ </a>

var myEnv = dotenv.config()
var myEnv = dotenv.config({ processEnv: {} }) // important to set processEnv: {}, otherwise expansion will be attempted on your already existing machine envs
dotenvExpand.expand(myEnv)

@@ -154,11 +160,12 @@

##### ignoreProcessEnv
##### processEnv
Default: `false`
Default: `process.env`
Turn off writing to `process.env`.
Specify an object to write your secrets to. Defaults to `process.env` environment variables.
```js
const myObject = {}
const dotenv = {
ignoreProcessEnv: true,
processEnv: myObject,
parsed: {

@@ -171,2 +178,3 @@ SHOULD_NOT_EXIST: 'testing'

console.log(obj.SHOULD_NOT_EXIST) // testing
console.log(myObject.SHOULD_NOT_EXIST) // testing
console.log(process.env.SHOULD_NOT_EXIST) // undefined

@@ -173,0 +181,0 @@ ```

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc