Skip to main content

Multi-Cloud Configuration

Atmos Design Pattern

The Multi-Cloud Configuration pattern describes how to organize your stacks so that the directory layout mirrors how your cloud provider organizes its resources. When what you see on disk matches how resources are deployed, navigation becomes intuitive and cognitive load drops.

Use-cases

Use the Multi-Cloud Configuration pattern when:

  • You are deploying infrastructure to Azure, GCP, or any non-AWS cloud

  • You manage infrastructure across multiple cloud providers

  • You are migrating between cloud providers and want a consistent organizational approach

Benefits

The Multi-Cloud Configuration pattern provides the following benefits:

  • Directory names use your cloud's own terminology, so engineers immediately understand the layout

  • The same Atmos features (imports, inheritance, catalogs) work identically regardless of cloud provider

  • Adding a new cloud is just adding a new directory tree — no changes to existing stacks

tip

These are not rigid guidelines. Atmos doesn't impose any particular directory structure — you can organize your stacks however you like. These patterns reflect what has worked well in practice: they reduce cognitive load, scale naturally as the number of services grows, and are logically justified by how each cloud provider organizes its resources.

Examples

Each cloud provider has a different resource hierarchy. The way you organize your infrastructure on disk should represent the predominant way that the cloud provider organizes its resources. This creates a logical relationship between what you see on disk and how it's deployed.

The following examples show how to structure stacks for each cloud, using that cloud's native terminology in folder names.

Directory Structure

AWS organizes resources as Organizations → Organizational Units → Accounts → Regions. The directory layout mirrors this hierarchy, with folders named after AWS concepts.

Organizing by account matters because each AWS account is a hard isolation boundary — it has its own IAM policies, billing, service quotas, and blast radius. When you see accounts/dev/ and accounts/prod/ on disk, you immediately know these are deploying to separate accounts with separate credentials and separate state. This prevents accidental cross-account deployments and makes it clear which account owns which resources.

   ├── stacks
│ ├── catalog
│ │ └── vpc
│ │ └── defaults.yaml
│ └── deploy
│ ├── _defaults.yaml
│ └── accounts
│ ├── dev
│ │ ├── _defaults.yaml
│ │ └── us-east-1.yaml
│ └── prod
│ ├── _defaults.yaml
│ └── us-east-1.yaml

└── components
└── terraform
└── vpc

Configure atmos.yaml

atmos.yaml

components:
terraform:
base_path: "components/terraform"

stacks:
base_path: "stacks"
included_paths:
- "deploy/**/*"
excluded_paths:
- "**/_defaults.yaml"
name_template: "{{.vars.stage}}-{{.vars.environment}}"

Configure Defaults

stacks/deploy/_defaults.yaml

vars:
namespace: acme

stacks/deploy/accounts/dev/_defaults.yaml

import:
- deploy/_defaults

vars:
stage: dev
account_id: "111111111111"

Configure Stack

stacks/deploy/accounts/dev/us-east-1.yaml

import:
- deploy/accounts/dev/_defaults
- catalog/vpc/defaults

vars:
region: us-east-1
environment: ue1

components:
terraform:
vpc:
vars:
ipv4_primary_cidr_block: "10.10.0.0/16"
availability_zones:
- us-east-1a
- us-east-1b
- us-east-1c

Provision

atmos terraform apply vpc -s dev-ue1

For deploying across multiple regions, see the Multi-Region Configuration pattern. For enterprise environments with multiple teams and accounts, see the Organizational Hierarchy pattern.

Cloud Organizational Concepts

Each cloud uses different terminology for how it organizes and groups resources. Understanding these mappings helps when translating directory structures between providers.

ConceptAWSAzureGCP
Top-level organizationOrganizationManagement GroupOrganization
Grouping / business unitOrganizational Unit (OU)Management GroupFolder
Isolation boundaryAccountSubscriptionProject
LocationRegionLocationRegion
Sub-locationAvailability ZoneAvailability ZoneZone

For more on multi-cloud integrations including authentication and stores, see the Multi-Cloud overview page.

Multi-Cloud Repositories

Teams working across multiple clouds typically use a monorepo strategy — a single repository that contains all the infrastructure configuration for a given scope. The main decision is how to segment that configuration: one repository per cloud, or one repository for all clouds.

Dedicated Repository per Cloud

The most common approach is a dedicated infrastructure repository for each cloud. Each repo uses that cloud's native directory conventions and can evolve independently. This is especially practical when different teams own different clouds or when each cloud has its own CI/CD pipelines and access controls.

   infra-aws/           # Dedicated AWS infrastructure
├── components/
└── stacks/
└── deploy/
└── accounts/

infra-azure/ # Dedicated Azure infrastructure
├── components/
└── stacks/
└── deploy/
└── subscriptions/

infra-gcp/ # Dedicated GCP infrastructure
├── components/
└── stacks/
└── deploy/
└── projects/

Single Repository for All Clouds

When a single team manages infrastructure across multiple clouds, or when cross-cloud coordination is important, a single repository with separate directory trees per cloud can work well.

   stacks
└── deploy
├── aws
│ └── accounts
│ └── ...
├── azure
│ └── subscriptions
│ └── ...
└── gcp
└── projects
└── ...

Application Repositories

The patterns above are designed for core infrastructure repositories — the ones that manage foundational resources like networking, identity, DNS, and databases. But not every repository needs that level of organizational depth. Application repositories that manage their own infrastructure typically only need to vary by SDLC environment (dev, staging, prod) while the foundational infrastructure is managed separately.

The Application SDLC Environments pattern provides a minimal flat structure for these repositories: one file per environment, co-located alongside application code, with everything else inherited as defaults. The two patterns work together — core infrastructure repos handle the foundation, and application repos manage just their slice.

References