cross-env vs dotenv vs env-cmd
环境变量管理工具
cross-envdotenvenv-cmd类似的npm包:

环境变量管理工具

环境变量管理工具用于在不同的环境中配置应用程序的设置。这些工具允许开发者在本地开发、测试和生产环境中灵活地管理环境变量,从而确保应用程序的配置一致性和安全性。使用这些工具可以简化环境变量的设置,避免在代码中硬编码敏感信息,提升应用程序的可移植性和安全性。

npm下载趋势

3 年

GitHub Stars 排名

统计详情

npm包名称
下载量
Stars
大小
Issues
发布时间
License
cross-env06,53120.2 kB16 个月前MIT
dotenv020,35093.3 kB81 个月前BSD-2-Clause
env-cmd01,81655.2 kB257 个月前MIT

功能对比: cross-env vs dotenv vs env-cmd

环境变量加载方式

  • cross-env:

    cross-env 通过 npm 脚本直接设置环境变量,确保在不同操作系统下的兼容性。它不直接处理环境变量文件,而是提供一个统一的命令行接口来设置环境变量。

  • dotenv:

    dotenv 通过读取 .env 文件,将环境变量加载到 process.env 中。它非常简单易用,适合在 Node.js 应用中使用,只需在应用启动时调用 require('dotenv').config() 即可。

  • env-cmd:

    env-cmd 允许你指定一个环境变量文件(如 .env),并在运行命令时加载这些变量。它支持多种文件格式,方便在不同环境之间切换。

跨平台支持

  • cross-env:

    cross-env 专为跨平台设计,确保环境变量在 Windows 和 Unix 系统上都能正常工作,解决了在不同操作系统中设置环境变量的复杂性。

  • dotenv:

    dotenv 主要用于 Node.js 环境,虽然它可以在不同操作系统上工作,但不专门处理跨平台的环境变量设置。

  • env-cmd:

    env-cmd 也支持跨平台使用,但主要依赖于命令行的环境变量设置,适合在不同环境中快速切换。

使用场景

  • cross-env:

    适用于需要在 npm 脚本中设置环境变量的场景,尤其是在 CI/CD 流程中,确保环境变量的一致性。

  • dotenv:

    适合在本地开发和测试中使用,方便管理应用程序的配置,尤其是当需要从文件中加载多个环境变量时。

  • env-cmd:

    适合在需要根据不同环境快速切换配置的场景,尤其是在开发和生产环境之间切换时。

配置灵活性

  • cross-env:

    cross-env 提供了简单的命令行参数来设置环境变量,灵活性较高,但不支持从文件中加载变量。

  • dotenv:

    dotenv 允许用户通过 .env 文件灵活配置环境变量,支持多行和注释,易于管理和维护。

  • env-cmd:

    env-cmd 提供了更高的灵活性,支持指定不同的环境文件,方便在不同环境之间切换,适合复杂的应用程序配置。

安全性

  • cross-env:

    cross-env 本身不处理敏感信息,但通过避免在代码中硬编码环境变量,可以提高安全性。

  • dotenv:

    dotenv 通过将敏感信息存储在 .env 文件中,避免在代码中暴露,提升了安全性,但需要确保 .env 文件不被上传到版本控制系统。

  • env-cmd:

    env-cmd 也支持从环境文件加载敏感信息,安全性与 dotenv 类似,但需要注意文件的管理和访问权限。

如何选择: cross-env vs dotenv vs env-cmd

  • cross-env:

    选择 cross-env 如果你需要在不同的操作系统(如 Windows 和 Unix)上统一设置环境变量,尤其是在 npm 脚本中。它提供了一个简单的方法来确保环境变量在所有平台上都能正常工作。

  • dotenv:

    选择 dotenv 如果你希望从 .env 文件中加载环境变量到 process.env 中,适合在 Node.js 应用程序中使用。它非常适合本地开发和测试,因为你可以轻松地管理和共享环境变量。

  • env-cmd:

    选择 env-cmd 如果你需要在命令行中运行脚本时动态加载不同的环境变量文件,适合在多种环境配置之间快速切换。它允许你指定不同的环境文件,方便管理多个环境。

cross-env的README

cross-env 🔀

Run scripts that set and use environment variables across platforms

🎉 NOTICE: cross-env is "done" as in it does what it does and there's no need for new features. Learn more


Build Status Code Coverage version downloads MIT License

The problem

Most Windows command prompts will choke when you set environment variables with NODE_ENV=production like that. (The exception is Bash on Windows, which uses native Bash.) Similarly, there's a difference in how windows and POSIX commands utilize environment variables. With POSIX, you use: $ENV_VAR and on windows you use %ENV_VAR%.

This solution

cross-env makes it so you can have a single command without worrying about setting or using the environment variable properly for the platform. Just set it like you would if it's running on a POSIX system, and cross-env will take care of setting it properly.

Installation

This module is distributed via npm which is bundled with node and should be installed as one of your project's devDependencies:

npm install --save-dev cross-env

WARNING! Make sure that when you're installing packages that you spell things correctly to avoid mistakenly installing malware

NOTE : Version 8 of cross-env only supports Node.js 20 and higher, to use it on Node.js 18 or lower install version 7 npm install --save-dev cross-env@7

Usage

I use this in my npm scripts:

{
	"scripts": {
		"build": "cross-env NODE_ENV=production node ./start.js --enable-turbo-mode"
	}
}

Ultimately, the command that is executed (using cross-spawn) is:

node ./start.js --enable-turbo-mode

The NODE_ENV environment variable will be set by cross-env

You can set multiple environment variables at a time:

{
	"scripts": {
		"build": "cross-env FIRST_ENV=one SECOND_ENV=two node ./my-program"
	}
}

You can also split a command into several ones, or separate the environment variables declaration from the actual command execution. You can do it this way:

{
	"scripts": {
		"parentScript": "cross-env GREET=\"Joe\" npm run childScript",
		"childScript": "cross-env-shell \"echo Hello $GREET\""
	}
}

Where childScript holds the actual command to execute and parentScript sets the environment variables to use. Then instead of run the childScript you run the parent. This is quite useful for launching the same command with different env variables or when the environment variables are too long to have everything in one line. It also means that you can use $GREET env var syntax even on Windows which would usually require it to be %GREET%.

If you precede a dollar sign with an odd number of backslashes the expression statement will not be replaced. Note that this means backslashes after the JSON string escaping took place. "FOO=\\$BAR" will not be replaced. "FOO=\\\\$BAR" will be replaced though.

Lastly, if you want to pass a JSON string (e.g., when using ts-loader), you can do as follows:

{
	"scripts": {
		"test": "cross-env TS_NODE_COMPILER_OPTIONS={\\\"module\\\":\\\"commonjs\\\"} node some_file.test.ts"
	}
}

Pay special attention to the triple backslash (\\\) before the double quotes (") and the absence of single quotes ('). Both of these conditions have to be met in order to work both on Windows and UNIX.

cross-env vs cross-env-shell

The cross-env module exposes two bins: cross-env and cross-env-shell. The first one executes commands using cross-spawn, while the second one uses the shell option from Node's spawn.

The main use case for cross-env-shell is when you need an environment variable to be set across an entire inline shell script, rather than just one command.

For example, if you want to have the environment variable apply to several commands in series then you will need to wrap those in quotes and use cross-env-shell instead of cross-env.

{
	"scripts": {
		"greet": "cross-env-shell GREETING=Hi NAME=Joe \"echo $GREETING && echo $NAME\""
	}
}

The rule of thumb is: if you want to pass to cross-env a command that contains special shell characters that you want interpreted, then use cross-env-shell. Otherwise stick to cross-env.

On Windows you need to use cross-env-shell, if you want to handle signal events inside of your program. A common case for that is when you want to capture a SIGINT event invoked by pressing Ctrl + C on the command-line interface.

Windows Issues

Please note that npm uses cmd by default and that doesn't support command substitution, so if you want to leverage that, then you need to update your .npmrc to set the script-shell to powershell. Learn more here.

Inspiration

I originally created this to solve a problem I was having with my npm scripts in angular-formly. This made contributing to the project much easier for Windows users.

Other Solutions

  • env-cmd - Reads environment variables from a file instead
  • @naholyr/cross-env - cross-env with support for setting default values

LICENSE

MIT