Workspace environment configuration¶
Separate environment-specific values (URLs, credentials, feature flags) from structural workspace config so the same workspace runs in dev, staging, and prod without editing workspace.yaml.
File layout¶
workspace/
├── workspace.yaml # structural — committed to git
├── workspace.env.yaml # environment — add to .gitignore
├── workspace.env.prod.yaml # optional per-environment override
├── topologies/
├── skills/
└── archetypes/
How it works¶
workspace.yaml uses ${property.path} references instead of inline values:
# workspace.yaml — safe to commit, no secrets
mcp_servers:
- id: github
transport: stdio
command: ["npx", "-y", "@modelcontextprotocol/server-github"]
env:
GITHUB_PERSONAL_ACCESS_TOKEN: ${github.token}
notifications:
- provider: slack
config:
webhook_url: ${notifications.slack.webhook_url}
channel: ${notifications.slack.channel}
workspace.env.yaml provides the actual values:
# workspace.env.yaml — NOT committed to git
# This is the ONLY file that does ${ENV_VAR} interpolation
github:
token: ${GITHUB_TOKEN}
notifications:
slack:
webhook_url: ${SLACK_WEBHOOK_URL}
channel: "#swarmkit-dev"
Resolution order¶
workspace.env.{SWARMKIT_ENV}.yaml— ifSWARMKIT_ENVis set and the file existsworkspace.env.yaml— default fallback${ENV_VAR}in property values — resolved from OS environment- Inline values in
workspace.yaml— backward compatible, used as-is if no${...}reference
Environment switching¶
# Dev (default — uses workspace.env.yaml)
swarmkit run my-swarm/ my-topology
# Production
SWARMKIT_ENV=prod swarmkit run my-swarm/ my-topology
# Staging
SWARMKIT_ENV=staging swarmkit run my-swarm/ my-topology
Each environment can have its own env file with different credentials, endpoints, and feature flags.
Two-phase interpolation¶
- Phase 1: Load env file → flatten nested YAML to dotted paths (
notifications.slack.channel→#swarmkit-dev) - Phase 2: Resolve
${ENV_VAR}in property values from OS environment (${GITHUB_TOKEN}→ actual token) - Phase 3: Replace
${property.path}references in workspace.yaml with resolved values
This means environment variables are only interpolated in the env file, not scattered across all YAML files.
Backward compatibility¶
Existing workspaces without workspace.env.yaml work unchanged. Property references (${...}) are only resolved if the ${} syntax is present. If you don't create an env file, nothing changes.
Best practices¶
- Add
workspace.env*.yamlto.gitignore— never commit credentials - Use
${ENV_VAR}only in the env file — keeps interpolation in one place - Create a
workspace.env.example.yamlwith placeholder values for team onboarding - Use named env files for each environment —
workspace.env.dev.yaml,workspace.env.staging.yaml,workspace.env.prod.yaml
Example¶
workspace.yaml (committed)¶
apiVersion: swarmkit/v1
kind: Workspace
metadata:
id: my-swarm
name: My Swarm
mcp_servers:
- id: github
transport: stdio
command: ["npx", "-y", "@modelcontextprotocol/server-github"]
env:
GITHUB_PERSONAL_ACCESS_TOKEN: ${github.token}
governance:
provider: agt
config:
policies_dir: ${governance.policies_dir}