-
Notifications
You must be signed in to change notification settings - Fork 0
Environment Variables
rsenv's environment hierarchy system eliminates duplication by letting child configurations inherit from parents.
Environment files form directed acyclic graphs (DAGs) where:
- Child files link to parents via
# rsenv: parent.envcomments - Variables are inherited and merged from parent to child
- Child values override parent values
- Multiple parents are supported for complex setups
base.env # Shared settings
├── local.env # Local dev (inherits base)
├── test.env # Testing (inherits base)
└── cloud.env # Cloud base (inherits base)
├── staging.env # Staging (inherits cloud)
└── prod.env # Production (inherits cloud)
Use # rsenv: to specify parent files:
# Single parent
# rsenv: base.env
# Multiple parents (space-separated)
# rsenv: base.env shared.env
# Path with variables
# rsenv: $RSENV_VAULT/envs/base.envrsenv parses export VAR=value lines:
# Standard export
export DATABASE_HOST=localhost
# With quotes
export MESSAGE="Hello World"
export PATH_VAR='$HOME/bin'
# Comments are preserved
# This is a comment
export DEBUG=true # inline comments work tooCompile a complete environment from a hierarchy:
rsenv env build path/to/leaf.envThis traverses all parents (breadth-first), merging variables. Child values override parents.
Example:
# base.env
export DATABASE_PORT=5432
export LOG_LEVEL=info
# local.env
# rsenv: base.env
export DATABASE_HOST=localhost
export LOG_LEVEL=debug
# Build
rsenv env build local.env
# Output:
# export DATABASE_PORT=5432 <- from base
# export DATABASE_HOST=localhost
# export LOG_LEVEL=debug <- overridden by local# Show tree structure
rsenv env tree [directory]
# Show all branches (linear)
rsenv env branches [directory]
# List leaf files only
rsenv env leaves [directory]
# List all files in a hierarchy
rsenv env files leaf.env# Fuzzy-select and update .envrc
rsenv env select [directory]
# Fuzzy-select and edit
rsenv env edit [directory]Note: This demo shows v1.5 syntax (
rsenv select). In v2, usersenv env selectinstead.
# Link parent to child
rsenv env link parent.env child.env
# Link chain: root <- middle <- leaf
rsenv env link root.env middle.env leaf.env
# Remove parent link
rsenv env unlink file.env# Build hierarchy and update .envrc vars section
rsenv env envrc leaf.env
# Write to specific file
rsenv env envrc leaf.env --envrc /path/to/.envrcThis command:
- Builds the environment hierarchy (same as
rsenv env build) - Updates only the vars section of the rsenv block (see Vault Management)
- Preserves header metadata and any content outside the rsenv section
Note: Requires an initialized project. Run rsenv init vault first.
Edit entire environment hierarchies in your vim editor:
rsenv env tree-edit <directory>-
Discovers all
.envfiles in the directory - Builds the hierarchy tree
- Opens all files simultaneously in your editor
- Arranges files hierarchically (parent-to-child)
When the same variable appears in multiple files, the last definition wins:
# base.env
export LOG_LEVEL=info
# middle.env
# rsenv: base.env
export LOG_LEVEL=warn
# leaf.env
# rsenv: middle.env
export LOG_LEVEL=debug
# rsenv env build leaf.env
# LOG_LEVEL=debug (leaf wins)With multiple parents, they're processed left-to-right:
# leaf.env
# rsenv: base.env overrides.env
# Processing order:
# 1. base.env (and its parents)
# 2. overrides.env (and its parents)
# 3. leaf.env itselfPaths in # rsenv: directives support:
-
$VARand${VAR}- environment variables -
~- home directory
# rsenv: $RSENV_VAULT/envs/base.env
# rsenv: ~/configs/shared.envAfter rsenv init vault, your vault's dot.envrc contains:
#------------------------------- rsenv start --------------------------------
# config.relative = true
# config.version = 2
# state.sentinel = 'myproject-abc12345'
# state.sourceDir = '$HOME/myproject'
export RSENV_VAULT=$HOME/.rsenv/vaults/myproject-abc12345
#-------------------------------- rsenv vars --------------------------------
export RUN_ENV=local
#-------------------------------- rsenv end ---------------------------------Use rsenv env envrc to update the vars section with your environment hierarchy:
rsenv env envrc $RSENV_VAULT/envs/local.envFor dynamic environment loading, add this after the rsenv section:
# After rsenv end - load hierarchy dynamically
eval "$(rsenv env build $RSENV_VAULT/envs/${RUN_ENV:-local}.env)"Set RUN_ENV to switch:
# Use local environment
export RUN_ENV=local
# Use production environment
export RUN_ENV=prod
# Reload
direnv allowUse interactive selection to update .envrc:
rsenv env select
# 1. Shows fuzzy finder with available environments
# 2. Updates .envrc with selection
# 3. Triggers direnv reloadvault/envs/
├── base.env # Truly shared settings
├── local.env # Local development
├── test.env # Test environment
├── ci.env # CI/CD pipelines
└── cloud/
├── base.env # Cloud-specific base
├── staging.env # Staging
└── prod.env # Production
Deep hierarchies (3+ levels) become hard to debug. Prefer:
- 2-3 levels for most projects
- Use multiple parents instead of deep chains
For clarity, use $RSENV_VAULT in directives:
# rsenv: $RSENV_VAULT/envs/base.env# Check if parent exists
ls -la $(dirname leaf.env)/parent.env
# Check path expansion
echo $RSENV_VAULTBuild order is breadth-first, then left-to-right for parents. Verify hierarchy:
rsenv env tree
rsenv env files leaf.env # Shows processing orderrsenv detects cycles and errors. Check your # rsenv: directives for loops.
- Core Concepts - Understanding the vault model
- Quick Start - Basic setup
- Vault Management - Managing vault structure
rsenv Documentation