Configuration
Table of Contents
Overview
Configuration is the process of defining how an application should behave in different environments. This article walks you through the core concepts, file formats, and recommended patterns for managing configuration safely and efficiently.
File Structure
Store configuration files in a dedicated config/ directory at the project root. A typical layout:
config/
├─ default.yaml
├─ development.yaml
├─ production.yaml
└─ secrets.yaml
Use default.yaml for common settings and override them in environment‑specific files.
Environment Variables
For secrets and values that differ per deployment, rely on environment variables. Example in .env:
DB_HOST=localhost
DB_USER=app_user
DB_PASS=SuperSecretPassword
Load them with a library such as dotenv and reference them in your configuration:
database:
host: ${DB_HOST}
user: ${DB_USER}
password: ${DB_PASS}
Dynamic Loading
Load the appropriate configuration at runtime based on the NODE_ENV (or equivalent) variable.
import yaml from 'js-yaml';
import fs from 'fs';
import path from 'path';
const env = process.env.NODE_ENV || 'development';
const base = yaml.load(fs.readFileSync(path.join('config','default.yaml'),'utf8'));
const specific = yaml.load(fs.readFileSync(path.join('config',`${env}.yaml`),'utf8'));
const config = {...base, ...specific};
export default config;
Best Practices
- Never commit secrets to version control.
- Validate configuration schema using a library like
ajvorzod. - Prefer explicit defaults over implicit fall‑backs.
- Document each configuration key.
- Separate runtime configuration from build‑time configuration.
Troubleshooting
If the application fails to start, verify the following:
- All required environment variables are set.
- Configuration files have valid YAML/JSON syntax.
- No secret values are accidentally overridden by defaults.
Use the built‑in validator to get detailed error messages:
npm run config:validate