tl;dr - You should be using
direnv to load ENV variables dynamically per-project.
You don’t necessarily have to buy into the entirety of the 12 factor app manifesto, but you should almost definitely be using ENV-as-configuration by this point.
Even if it’s just a
CONFIG ENV var that points to a
config.toml that your application reads, passing configuration via environment variables is the tried and true method of configuring applications these days (inside a docker container or out).
But how do you manage your ENV configuration when doing local development? Well that’s where
direnv comes in.
If you place a
.env) file in a directory, and browse to it in your shell of choice,
direnv will load those ENV variables.
Check out the install instructions to get
direnv installed, then make a
.envrcfile like this:
# let's say you want to use the superior editor export EDITOR=emacs # and the superior browser export BROWSER_BIN=firefox-developer-edition # Application variables # (these are what your application needs to run) export FOO=bar
In addition to just values, you can put whatever you want in your
.envrc and it will be evaluated… Which means you can do a lot with
One example You could get the absolute path to a file or even read it into an ENV var.
# You can get the absolute path to a file export ABS_PATH_TO_FILE=$(realpath relative/path/to/file) # You can also read files into ENV vars export FILE_IN_VAR=$(cat relative/path/to/small/file)
NOTE: you’ll need
realpath installed of course, but you could run any other command as well
One of my favorite uses is to trigger/configure
git to do hooks, avoiding the need to use tools like
# While in the project folder tree, git will load hooks from `.githooks` (which can be checked into source control!) git config --local core.hooksPath $PWD/.githooks
.envfiles work too!
Whether you’re developing a NodeJS app that expects
.env files, or you’re working with a file that could be passed to
--envfile), you can configure
In the configuration file for
~/.config/direnv/direnv.toml) you can add a configuration like this:
[global] load_dotenv = true
This will enable
direnv to read
.env files which have a slightly different syntax and are less dynamic:
.dockerignoreyour .env files!
If you’re going to use
direnv, don’t forget to add
.env to your
.gitignore if you don’t want to check the files in!
You could ignore the files for every repo on your own computer, but the best way to make sure that no one on your team checks the file in either is to put the
.gitignore (which includes
.env) into source control.
direnv is super flexible and I’ve loved having it as part of my go-to tooling for a long time. If you haven’t already, start using it!