How it works¶
The change lifecycle¶
A change to the landing zone is a pull request. From there the engine drives the whole flow.
sequenceDiagram
actor Eng as Engineer
participant PR as Pull request
participant Res as resolve (hosted)
participant Run as run / apply (self-hosted)
participant Az as Azure
Eng->>PR: open PR touching a unit
PR->>Res: parse event, select impacted units
Res->>Run: matrix of units to plan
Run->>Az: OIDC login, terraform plan
Az-->>Run: plan result
Run->>PR: post plan comment + gate output
Eng->>PR: review, comment /apply
PR->>Res: approval gate (required reviews)
Res->>Run: apply in dependency order
Run->>Az: terraform apply
Run->>PR: post apply comment
PR->>PR: merge gate turns green
Eng->>PR: merge
What each step does¶
- Open or update a PR. The
resolvejob parses the event, works out which files changed, and selects the impacted units. In Terragrunt mode it uses native discovery to include a changed unit plus every downstream dependent, in dependency order. On a/planor/applycomment it checks out the PR head before discovery, so a unit that exists only on the PR branch is selected. - Plan. The
runjob fans out one job per impacted unit, in parallel, on the self-hosted runner. Each unit logs in to Azure with the read-only plan identity, runsterraform plan, and runs thepost_plangates. - Report. Each unit posts a fresh comment on the PR, led by a validation check, then the plan output, a change summary table, apply instructions, and the gate findings (collapsed when clean, expanded on a finding). A per-unit check appears in the PR checks, and the engine reacts to the command comment: 👀 seen, 🚀 running, 🎉 or 👎 when it finishes.
- Review and apply. A reviewer approves. Someone comments
/apply. The approval gate confirms the PR meets the repo's required reviews, then a single apply job applies the units in dependency order, one at a time, skipping any unit whose dependency failed. - Merge gate. A status check named
tf-pr-ops / merge-gateis green only when the PR has no Terraform changes, is a no-op, or has been fully applied. It blocks when the PR changed Terraform but no unit was selected, so an unapplied net-new or removed unit cannot merge green. Make it a required check and unapplied changes cannot reach the main branch.
Commands¶
Most of the flow is automatic. The commands you type are comments on the PR:
| Comment | Effect |
|---|---|
/plan |
Re-plan all changed units. |
/plan -p <label> |
Plan one unit. |
/apply |
Apply all changed units in dependency order. |
/apply -p <label> |
Apply one unit. |
digger plan and digger apply are accepted as aliases, so a team migrating
from Digger keeps its muscle memory. See the full
Command reference.
Drift, in the background¶
Separately, a scheduled job plans every unit read-only against the live tenant once a day and opens a GitHub Issue for each unit that has drifted, closing it again when the unit comes back clean. See Drift detection.
Gates, on every plan¶
Every plan (and every drift plan) runs three checks against the plan: a conftest policy check, a checkov security scan, and an infracost cost estimate. They start advisory and you enforce them when ready. See Policy, security, and cost gates.