Continuous Version Deployment
Continuous Version Deployment is the recommended trunk-based deployment strategy where environments progressively converge to whatever component path they reference in stack configurations. All environments work from the main branch trunk, with automated testing and deployment pipelines controlling progressive rollout. This strategy decouples release from deployment using automation rather than version control strategies, promoting automated convergence while maintaining safety through comprehensive testing.
This strategy represents the sweet spot for most organizations—simple enough to understand and operate, yet powerful enough to handle complex deployment scenarios. By deploying all environments from the same trunk and using automation to control the rollout, teams can move fast with confidence while maintaining visibility into change impacts across their entire infrastructure.
Within this strategy, you can organize your components using different folder structures depending on your needs: simple Folder-Based Versioning, Release Tracks/Channels, or Strict Version Pinning.
This deployment strategy supports multiple folder organization approaches. Most components use simple folder-based versioning, while specific components requiring planned divergence can use release tracks or strict version pinning. See the Planned Divergence section for detailed examples of combining approaches.
You will learn
- All environments deploy commits from the main branch trunk (trunk-based development)
- Environments converge to the same commit through automated progressive rollout
- Controlled, time-bound divergence during deployment pipeline execution
- Changes are immediately visible across all environments during planning
- Automation drives convergence, reducing operational overhead and drift
Strategy Overview
Continuous Version Deployment is the overarching trunk-based deployment strategy where environments progressively converge to whatever component path they reference in their stack configurations. The key principle: whatever component folder your stack references, your environment will converge to that version through automated progressive rollout.
Instead of managing different versions per environment through Git branching, you use:
- Automated testing pipelines to validate changes before they reach production
- Progressive deployment strategies to roll out commits incrementally across environments
- Environment-specific configuration to control behavior per environment
- CI/CD automation to orchestrate the convergence process
This approach aligns with modern DevOps practices and trunk-based development, where the main branch is always deployable and releases are controlled through automation. Environments naturally diverge during the rollout window (while the pipeline executes), then automatically converge once the deployment completes.
Folder Organization Approaches
Within this deployment strategy, you can organize your component folders in different ways depending on your needs:
Folder-Based Versioning - The foundational approach with simple folders (vpc/, eks/, rds/). All environments typically reference the same component folder and converge to it. This is the recommended starting point and what most teams use for most components.
Release Tracks/Channels - Organizes components into named channels (alpha/vpc, beta/vpc, prod/vpc). Environments subscribe to tracks and converge to whatever version is in their track.
Strict Version Pinning - Uses explicit SemVer versions (vpc/1.2.3, vpc/2.0.0). Works well when vendoring from external sources or managing shared component libraries.
All these approaches share the same deployment philosophy: environments converge to the component path they reference through progressive automated rollout.
These folder organization approaches work seamlessly with Vendoring Component Versions. Atmos makes explicit what other tools do implicitly—instead of just-in-time cloning to temp folders, we vendor components locally for visibility, searchability, and operational control. See the Component Sourcing Philosophy for why this approach emerged from countless projects.
How It Works
Basic Structure
All your stack configurations reference the same components without version qualifiers:
- Development
- Staging
- Production
Deployment Pipeline
The key to this pattern is a robust deployment pipeline that validates changes progressively. Your CI/CD system orchestrates the convergence process:
Validation Stage (on pull request):
- Run
terraform validateand security scans (tfsec, checkov, etc.) - Execute policy checks (OPA, Sentinel)
- Generate and display terraform plans for all environments
- Provide visibility into what will change across dev, staging, and production
Progressive Deployment (after merge to main):
- Dev deployment: Automatically deploy to development environment
- Dev validation: Run smoke tests and basic functionality checks
- Staging deployment: Deploy to staging after dev validation passes
- Staging validation: Execute comprehensive integration and performance tests
- Production approval: Require manual approval or wait for time-based gate
- Production deployment: Deploy to production with monitoring
- Production validation: Post-deployment health checks and alerting
Monitoring & Rollback:
- Track deployment metrics and error rates
- Configure automated alerts for anomalies
- Maintain rollback procedures (revert commit + re-run pipeline)
Decoupling Release from Deployment
A core principle of this pattern is separating deployment (putting code in an environment) from release (making changes available to users). The industry has established that this decoupling increases speed and stability.
Decoupling deploy from release increases speed and stability when delivering software.
More-frequent deployments reduce the risk associated with change, while business stakeholders retain control over when features are released to end users.
While application teams often achieve this through runtime feature flags (LaunchDarkly, Thoughtworks Feature Toggles), infrastructure-as-code benefits from a different approach:
Atmos decouples through progressive deployment automation - where CI/CD gates control when environments receive changes, and comprehensive plan previews enable informed release decisions.
How Atmos Achieves Decoupling
Deployment: Merge to main declares intent to deploy everywhere
Release: CI/CD gates control WHEN each environment actually gets the changes
Preview: See the impact on ALL environments before releasing to ANY
Atmos's Key Advantage: Unlike approaches requiring version pinning updates, you see the plan for every environment immediately after merge—dev, staging, AND production—without touching any configuration. This visibility enables informed decisions about release timing.
Knowing that deploying new code will not automatically trigger a release provides that safety net.
This decoupling is achieved through two separation mechanisms:
-
Environmental Configuration Separation: Stack configurations (stacks/dev/, stacks/staging/, stacks/prod/) provide environment-specific variables and settings, allowing the same component to behave differently per environment.
-
Component Version Separation: The
metadata.componentpath determines which component implementation to use, enabling environments to reference different versions through folder organization.
The primary mechanism controlling when deployments are released to each environment is CI/CD approval gates (GitHub Actions, GitLab CI, etc.). These gates control the progression of deployments across environments through automated testing, manual approvals, and time-based holds—more natural for infrastructure than runtime flags while achieving the same goal.
| Approach | Mechanism | Decoupling Method | Best For |
|---|---|---|---|
| Feature Flags (LaunchDarkly) | Runtime switches | Control feature visibility in deployed code | Application features with gradual rollout needs |
| Atmos | CI/CD gates + automation | Control deployment timing across environments | Infrastructure changes with progressive validation |
Environment-specific configuration (Terraform variables, Helm values) provides the most natural way to control infrastructure behavior per environment. While runtime feature flags can supplement this, they add complexity in infrastructure-as-code compared to application development, so they're best reserved for specific use cases rather than general practice.
Progressive Rollout Across Environments
When you merge code to main, you're declaring you want this code live in all environments (dev, staging, prod). However, progressive rollout means deploying to environments sequentially with approval gates:
- Deploy to dev - Automatically after merge
- Let it sit - Validate in dev environment
- Approve deployment to staging - Manual or automated gate
- Validate in staging - Pre-production testing
- Approve deployment to production - Manual approval gate
- All environments converged - Same code running everywhere
This progressive environment rollout provides safety through validation at each stage while driving convergence across all environments.
Experimentation
Experimentation in Atmos is achieved through folder-based component isolation. When you need to test a new approach or validate an experimental change, create a dedicated component folder for your experiment and pin specific environments to it. This clearly signals that the environment has deliberately diverged, making the experiment visible in both the file system and stack configuration.
Creating an Experiment
Pinning Environment to Experiment
- Development
- Production
Experiment Lifecycle
- Create experiment folder - Copy stable component to new folder (e.g.,
vpc-experiment) - Make changes - Modify experimental component without affecting stable
- Pin test environment - Update dev/staging to reference experiment folder
- Validate - Test experimental changes in isolated environment
- Promote or discard:
- Success: Merge changes back to stable component, remove experiment folder
- Failure: Delete experiment folder, revert environment pins
This approach provides complete isolation for experiments while maintaining the benefits of trunk-based development. Each experiment is visible in the repository structure and can be managed through standard Git workflows.
Understanding Divergence
All deployment systems experience periods where environments are in different states—this is unavoidable. The question isn't whether divergence exists, but rather: Is it controlled, visible, and temporary?
Operational Divergence
During progressive rollout, environments naturally diverge as commits flow through your pipeline:
Time 0: Commit abc123 merged to main
├─ Dev: abc123 (deployed automatically)
├─ Staging: xyz789 (previous commit, divergence begins)
└─ Prod: xyz789 (previous commit)
Time +30min: Dev validation passes
├─ Dev: abc123 ✓
├─ Staging: abc123 (deployed after dev validation)
└─ Prod: xyz789 (still on previous commit)
Time +2hrs: Staging validation passes, manual approval
├─ Dev: abc123 ✓
├─ Staging: abc123 ✓