envdiff
Compare and validate .env files. Catch missing variables before they crash production.
$ envdiff .env.example .env
MISSING in .env:
✗ STRIPE_SECRET_KEY
✗ AWS_REGION
EXTRA in .env:
+ SENTRY_DSN
DIFFERENT values:
≠ DATABASE_URL (masked)
≠ JWT_SECRET (masked)
EMPTY values:
⚠ REDIS_URL (empty in .env)
Why
Every developer has deployed with a missing env variable. .env.example exists as a convention, but nobody validates against it. diff shows raw values (security risk) and doesn't understand key-value structure.
envdiff compares by key, masks values by default, and exits with code 1 when variables are missing. Drop it into CI and never ship with missing env vars again.
Features
- Key-based comparison — compares by variable name, not line position
- Value masking — secrets are hidden by default
- Auto-detection —
envdiff check finds .env.example / .env.sample / .env.template automatically
- CI-ready —
--ci flag outputs JSON and sets exit codes
- Colored output — missing (red), extra (yellow), different (cyan), empty (warning)
- Cross-platform — single binary for Linux, macOS, and Windows
- Zero config — works out of the box, no setup needed
Install
Go install
go install github.com/freedom07/envdiff@latest
Download binary
Download the latest release from GitHub Releases:
# macOS (Apple Silicon)
curl -sL https://github.com/freedom07/envdiff/releases/latest/download/envdiff_0.1.0_darwin_arm64.tar.gz | tar xz
sudo mv envdiff /usr/local/bin/
# macOS (Intel)
curl -sL https://github.com/freedom07/envdiff/releases/latest/download/envdiff_0.1.0_darwin_amd64.tar.gz | tar xz
sudo mv envdiff /usr/local/bin/
# Linux (amd64)
curl -sL https://github.com/freedom07/envdiff/releases/latest/download/envdiff_0.1.0_linux_amd64.tar.gz | tar xz
sudo mv envdiff /usr/local/bin/
Build from source
git clone https://github.com/freedom07/envdiff.git
cd envdiff
go build -o envdiff .
Usage
Compare two files
envdiff .env.example .env.production
Compare any two .env files. Shows missing, extra, different, and empty variables.
Validate against .env.example
envdiff check
Automatically finds .env.example (or .env.sample, .env.template) in the current directory and compares against .env.
CI mode
envdiff check --ci
Outputs JSON and exits with code 1 if required variables are missing. Use in CI/CD pipelines:
GitHub Actions:
steps:
- uses: actions/checkout@v4
- name: Install envdiff
run: go install github.com/freedom07/envdiff@latest
- name: Validate env vars
run: envdiff check --ci
GitLab CI:
validate-env:
script:
- go install github.com/freedom07/envdiff@latest
- envdiff check --ci
Show values
envdiff .env.example .env --show-values
Warning: This reveals secret values in the terminal output.
JSON output
envdiff .env.example .env --format json
{
"source": ".env.example",
"target": ".env",
"missing": [{"key": "STRIPE_SECRET_KEY"}, {"key": "AWS_REGION"}],
"extra": [{"key": "SENTRY_DSN"}],
"ok": false
}
Commands & Flags
| Command / Flag |
Description |
envdiff [file1] [file2] |
Compare two .env files |
envdiff check |
Validate .env against .env.example (auto-detected) |
--ci |
JSON output + exit 1 if missing keys |
--format json |
JSON output |
--show-values |
Reveal masked values (use with caution) |
--version |
Print version |
Exit Codes
| Code |
Meaning |
0 |
No missing variables |
1 |
Missing variables found, or file error |
Extra, different, and empty values are warnings only (exit 0). Only missing keys trigger exit 1.
Parser Support
| Pattern |
Example |
Supported |
| Key-value |
DATABASE_URL=postgres://... |
✅ |
| Comments |
# this is a comment |
✅ |
| Empty values |
API_KEY= |
✅ (warning) |
| Export prefix |
export NODE_ENV=production |
✅ |
| Double quotes |
SECRET="my secret" |
✅ |
| Single quotes |
SECRET='my secret' |
✅ |
| Multiline (double quotes) |
CERT="line1\nline2" |
✅ |
| Escape sequences |
MSG="say \"hello\"" |
✅ |
Roadmap
- Multi-environment matrix (
envdiff matrix dev.env staging.env prod.env)
-
--ignore KEY and --required KEY flags
- GitHub Action (
uses: freedom07/envdiff-action@v1)
- Git pre-commit hook integration
- Type validation (URL, number, boolean)
Contributing
Contributions are welcome! See CONTRIBUTING.md for guidelines.
Security
Values are masked by default. See SECURITY.md for our security policy and how to report vulnerabilities.
License
MIT — use it however you want.