EnvGraph is a developer tool that analyzes project configuration and generates an interactive graph showing where environment variables come from and where they are used.
Modern applications spread configuration across many places:
.envfiles- Docker Compose
- source code
- deployment files
- CI/CD configuration
EnvGraph helps answer:
- Where does this environment variable come from?
- Where is it passed?
- Which part of the application uses it?
- Which configuration values are missing or unused?
Instead of manually searching:
grep -R DATABASE_URL .EnvGraph creates a visual flow:
.env
DATABASE_URL
|
v
docker-compose.yml
|
v
api container
|
v
config/database.go
|
v
PostgreSQL connection
Detect relationships between:
- configuration files
- containers
- environment variables
- application code
Explore your project's configuration structure visually.
Understand:
- sources
- consumers
- dependencies
- configuration flow
Find variables that are used but not provided.
Example:
JWT_SECRET
Used in:
auth/config.go
Source:
missing
Identify configuration values that exist but are never used.
Example:
OLD_API_KEY
Defined in:
.env
Usage:
none
| Source | Status | Detects |
|---|---|---|
.env files |
Supported | assignments, quoting, multi-line values |
| Docker Compose | Supported | environment, env_file, ${VAR} substitution |
| Dockerfile | Supported | ENV, ARG, $VAR in values, continuations |
| Go | Supported | os.Getenv, os.LookupEnv |
| Python | Supported | os.getenv, os.environ[...], environ.get |
| JavaScript / TypeScript | Supported | process.env, import.meta.env, destructuring |
| GitHub Actions | Supported | env: at every level, ${{ }} expressions, run: scripts |
| Kubernetes manifests | Planned |
More sources will be added gradually.
go install github.com/PeacexF/EnvGraph/cmd/envgraph@latestOr build from a checkout:
go build -o envgraph ./cmd/envgraphAnalyze a project and print its configuration flow:
envgraph scan .DATABASE_URL ok
source .env:2
passed to api (docker-compose.yml:5)
used in config/database.go:7
Trace one variable end to end:
envgraph explain DATABASE_URLDATABASE_URL ok
from .env:2
into api (docker-compose.yml:5)
worker (docker-compose.yml:15)
read config/database.go:7
For a variable that is missing it says what to do about it, and it answers
even for variables an ignore rule hides from everything else.
Fail when configuration is missing, which makes it usable as a CI step:
envgraph check .Exits with status 1 when a variable is used but never provided. Pass
--strict to fail on unused variables too.
Explore it in a browser:
envgraph serve .Opens an interactive graph on http://127.0.0.1:8080. The layout is a live
force simulation — drag a node and its neighbours follow, or switch Physics
off to freeze it. Click a node for where a variable comes from and where it
goes; filter to missing or unused. The project is re-scanned on every request,
so a reload picks up your edits.
Values are never sent to the browser unless you pass --show-values.
Write the graph as JSON:
envgraph export . # writes graph.json
envgraph scan . -f json # the analysis and the graph togetherUseful flags:
| Flag | Effect |
|---|---|
--only <status> |
list only ok, missing, or unused |
--exclude <dir> |
skip additional directories |
--ignore <name> |
drop variables, glob wildcards allowed |
--include-tests |
count usage in test files |
--show-values |
include assigned values (these are often secrets) |
--config <file> |
use a specific .envgraph.yml |
--no-config |
ignore the config file and the system defaults |
-o <file> |
write to a file instead of stdout |
Workflows are read the way containers are: each job becomes a node, and variables flow into it.
DEPLOY_TOKEN missing
source (none)
passed to deploy (.github/workflows/deploy.yml:35)
used in .github/workflows/deploy.yml:35
That is the case worth catching — a run: script reads $DEPLOY_TOKEN, no
env: block or secret supplies it, and the failure only shows up when the
job runs. Variables the runner provides itself (GITHUB_*, RUNNER_*,
ACTIONS_*) are ignored by default, as are shell locals: a name a script
assigns to itself, loops over, or reads is not configuration.
Drop an .envgraph.yml in the project root to stop reporting things you do
not care about. Every command reads it, and an ignored variable disappears
from the report and the graph alike.
# Directory names to skip, the same as --exclude.
exclude:
- examples
- testdata
# Variables to drop. Wildcards allowed.
ignore:
- OLD_API_KEY
- "VITE_*"
# Variables set by the shell, the OS, or the CI runner — PATH, HOME, CI,
# NO_COLOR and friends — are ignored by default. Set this to false to see them.
systemVariables: trueWithout this, a real project reports noise: a Dockerfile that extends PATH
looks like it defines an unused variable, and committed fixtures look like
broken configuration. EnvGraph ships its own for exactly that
reason.
Try it against the bundled examples:
envgraph scan examples/simple-go
envgraph check examples/compose-python
envgraph serve examples/node-appReal runs on real projects, showing how it all works
A variable is missing when nothing supplies a value for it. What counts as supplying a value is deliberately strict:
| Written as | Counts as a source? |
|---|---|
DATABASE_URL=postgres://... in .env |
yes |
LOG_LEVEL: info in compose |
yes |
PORT: ${PORT:-8080} in compose |
yes, via the fallback |
ENV PORT=3000 in a Dockerfile |
yes |
ARG VERSION=1 in a Dockerfile |
yes, via the default |
ARG VERSION in a Dockerfile |
no — it needs --build-arg at build time |
KEY: ${{ secrets.KEY }} in a workflow |
yes — GitHub supplies it |
KEY: ${{ vars.KEY }} / ${{ inputs.x }} |
yes, same reasoning |
$KEY in a workflow run: script |
no — reading is not providing |
DATABASE_URL: ${DATABASE_URL} |
no — it passes a value along without supplying one |
- DATABASE_URL in compose |
no — it forwards a host variable |
DB_HOST: ${POSTGRES_HOST} renames a variable on the way into a container.
DB_HOST is treated as supplied exactly when POSTGRES_HOST is.
A variable is unused when it has a source but nothing reads it — neither application code nor a container it is passed to.
EnvGraph consists of three main parts:
CLI
|
Scanner
|
Graph Engine
|
Web Viewer
Finds configuration sources and consumers.
Builds relationships between configuration nodes.
Displays the configuration flow interactively. Built from plain ES modules
with a vendored Cytoscape.js, compiled into the binary with go:embed, so
go build remains the only build step and there is nothing to install.
Configuration is one of the hidden complexities of modern applications.
A project may have:
.env
docker-compose.yml
application config
source code
CI variables
but no clear overview of how values move through the system.
EnvGraph provides that missing layer of visibility.
| Document | For |
|---|---|
| Guide | Commands, configuration, and how EnvGraph decides what is missing |
| Architecture | How it works inside, and how to add a new configuration source |
Contributions are welcome.
Please read CONTRIBUTING.md before submitting changes, and docs/architecture.md for how the pieces fit together.