Appearance
Environments
An app can have multiple environments, such as staging and production. Every Keel command targets one app and environment. Define environments under environments: in keel.yml; Keel merges each environment's overrides into the app-level configuration.
yaml
name: acme-api
region: us-east-1 # app default region
environments:
staging:
# no account override → shares the app's account, isolated by name prefix
services:
web:
desired_count: 1
production:
region: us-east-1
account: "111111111111" # opts into a separate AWS account
services:
web:
desired_count: 3
cpu: 1024
database:
instance: db.r6g.large
default_environment: productionIf environments: is omitted, Keel operates on a single synthetic default environment.
Isolation models
Two isolation models are supported, selectable per environment:
- Namespace isolation (default): Environments share an AWS account and use an
<app>-<env>prefix. Because Keel roles are account-wide, environments in the same account share credentials. - Account isolation: Set
accountand, optionally,regionto place an environment in another AWS account. Each account-isolated environment stores credentials under~/.keel/contexts/<app>/<env>/and requireskeel auth setuporkeel auth joinin that account.
Resource names, OpenTofu state keys, SSM paths, log groups, and registry entries include the app and environment names.
How overrides merge
Overrides are merged field by field, so a block only has to name what differs:
| Section | Merge rule |
|---|---|
database, cache, domain | field by field; unset fields inherit the base |
services.<name> | field by field |
services.<name>.environment, top-level environment, tags | merged per key; the override wins |
secrets (app or service) | union by name; order follows the base |
bindings | merged by resource; an override replaces that one entry |
permissions | appended |
resources | merged per resource name |
release, waf | replaced whole |
For example, a database.instance override inherits the base block's engine, version, storage, and multi_az values. This field-level merge prevents an environment override from resetting unrelated boolean or count fields.
Selecting an environment
Precedence, highest first:
--env <name>flagKEEL_ENVenvironment variable- The active environment set with
keel env use <name>(persisted under~/.keel) default_environmentinkeel.yml
bash
keel env list # list environments and see which one is active
keel env use staging # persist the active environment for this app
keel env current # print the environment the current context targets
keel deploy web --env production # override for a single commandAdding an environment
keel env add declares a new environment by editing keel.yml in place — comments and key order survive:
bash
keel env add staging
keel env add production --env-region us-east-1 --account 111111111111When you add the first named environment, Keel also writes the existing implicit default environment and keeps it as the default, preserving the current stack name. Run keel up --env <name> to provision the new environment. You can also add an environment from the dashboard with e.