Overview
Delivery engineering is the machinery between "merged" and "serving users": continuous integration proving every change, pipelines that build once and promote the same artifact, and deployment strategies that make releases boring. The research backbone is Accelerate (Forsgren, Humble, Kim): the four DORA metrics — lead time, deploy frequency, change failure rate, time to restore — tie delivery practice to organizational performance.
Key points
- Trunk-based development: short-lived branches (hours, not weeks) merged into an always-releasable main; long-lived feature branches trade merge pain for false safety. CI means integrating continuously, not just running tests on PRs.
- Pipeline principles: build the artifact once, promote it through environments; fast feedback first (lint/unit in minutes), slower suites staged after; pipeline as code, reproducible builds.
- Decouple deploy from release: feature flags let code ship dark and turn on per cohort — enabling trunk-based work, kill switches, and A/B tests; flag debt is real, retire them.
- Progressive deployment: blue/green (instant switch, easy rollback), canary (shift a slice of traffic, watch the metrics, promote or roll back), rolling; automated rollback on SLO burn is the mature end-state.
- Database changes are the hard part: expand → migrate → contract, never a breaking change in one deploy; migrations versioned and forward-only.
- Supply chain hygiene: pinned dependencies, signed artifacts, SBOMs — the pipeline is an attack surface (see the Security theme).
- To explore: GitOps (declared state, reconciliation), merge queues, ephemeral preview environments, platform engineering as the productized form of all this.
The pipeline shape — one artifact, built once, promoted:
flowchart LR
F["Fast feedback first - lint and unit tests in minutes"] --> SL["Slower suites, staged after"]
SL --> B["Build the artifact once"]
B --> Stg["Staging"]
Stg --> Prod["Production"]
B -.->|the same artifact is promoted through environments| Prod
And the database half, spread over three deploys so no single deploy breaks anything:
flowchart LR
D1["Deploy 1: expand"] --> D2["Deploy 2: migrate"] --> D3["Deploy 3: contract"]
Practice
- Staged pipeline for a toy service (source) — build a GitHub Actions pipeline that lints and unit-tests in minutes, then builds one artifact and promotes that same artifact through staging to "prod"; teaches build-once-promote and fast-feedback staging on your own code.
- Expand–migrate–contract drill (source) — rename a column on a toy app under live traffic in three deploys, never a breaking change in one; teaches the database half of zero-downtime delivery.
- Home-made feature flag (source) — ship a feature dark behind your own flag with a percentage rollout and a kill switch, then retire the flag; teaches deploy/release decoupling and flag debt in miniature.
- Canary with Argo Rollouts (source) — replace a Deployment with a Rollout, shift traffic in steps against a metric, and trigger an automated rollback by shipping a bad version on purpose; teaches progressive delivery end to end.
- GitOps loop with Argo CD (source) — deploy an app purely by committing manifests, then break the live state by hand and watch reconciliation repair it; teaches declared-state delivery as a build project.
Related
- Observability & SRE practice — canaries and error budgets are the same feedback loop.
- Microservice architecture — one service = one pipeline is half the point.
- TDD — the test suite CI leans on.
- Developer environments — the pipeline is one more machine needing the project's toolchain; the same versions should reach both.
- Version pinning & currency — the supply-chain hygiene bullet above, worked out in full.
- Test-suite scheduling & job partitioning — why a slow pipeline is usually floored by one unit rather than starved of workers.