Configuration is the part of an application that varies between deployments, and the discipline of managing it well separates code that runs identically everywhere from code that fails mysteriously when moved. The Twelve-Factor methodology states the principle plainly: configuration that differs across environments should live in the environment, not in the codebase. This article explains why that separation matters, how environment variables implement it, and how secrets, a special and more dangerous category of configuration, must be handled to keep credentials out of source control and out of the wrong hands.
Why Configuration Belongs in the Environment
The Twelve-Factor App defines configuration as everything likely to vary between deploys: database connection strings, credentials for external services, and per-deployment hostnames. The methodology proposes a concrete test of whether configuration has been correctly separated from code. Could the codebase be made open source at any moment without compromising any credentials? If the answer is no, secrets have leaked into the code.
The reasoning is that code and configuration change for different reasons and at different rates. Code is the same across every deployment; configuration is precisely what differs between a developer’s machine, a staging environment, and production. Binding them together forces a code change for every environmental difference and invites the accidental commit of a production credential into version control, where it persists in history long after it is removed from the current files.
Environment Variables as the Mechanism
The methodology recommends storing configuration in environment variables. These are variables held by the operating system process rather than in a file tracked by the repository. They are straightforward to change between deploys without altering code, they are language-agnostic, and they are supported by every operating system and deployment platform.
A practical advantage is granularity. Each configuration value is an independent variable, which avoids the tendency of configuration files to accumulate named groupings, such as “development” or “production,” that multiply unmanageably as deployments proliferate. With environment variables, a new deployment is described by a new set of values rather than a new named bundle in code.
The Special Case of Secrets
Some configuration values are merely environmental, such as a port number. Others are secrets: API keys, database passwords, signing keys, and tokens whose disclosure causes direct harm. Secrets are configuration, but they demand stricter handling.
The first rule is that secrets never enter source control. A file containing real credentials must be excluded from the repository, commonly through an ignore rule, while a committed example file documents which variables are required without supplying their values. The second rule is that secrets are injected at deploy time by the platform rather than printed in logs or embedded in build artifacts.
Deployment platforms provide facilities for exactly this. Vercel, for instance, allows environment variables to be defined per project and scoped to specific environments such as production, preview, and development, so that a preview deployment does not receive production credentials. Sensitive values are stored by the platform and supplied to the running application rather than living in the repository. This arrangement satisfies the Twelve-Factor test directly: the codebase can be inspected freely because the secrets are not in it.
Practices That Hold Up
Several habits reduce risk in practice. Maintain an example file listing every required variable so that a new engineer or a new environment can be configured without guesswork. Scope secrets to the narrowest environment that needs them, keeping production credentials away from preview and development. Rotate any secret that may have been exposed, treating a credential that once appeared in a commit as compromised regardless of later removal. Finally, distinguish between values safe to expose to a client, such as a public identifier, and values that must remain server-side, and never let a build process embed the latter into client-delivered code.
Conclusion
Environment variables exist to keep configuration out of code, and their disciplined use produces applications that move between environments without modification. Secrets are configuration with consequences, and they require an additional layer of care: exclusion from source control, injection at deploy time, scoping to the minimum environment, and rotation when exposed. The Twelve-Factor test remains the clearest measure of success. If the codebase could be published without leaking a single credential, configuration has been managed correctly, and the platform’s secret-handling features are doing the work that source control should never be asked to do.