ADR 0021: Continuous delivery — GitHub Actions and GitHub Container Registry

Ratification

Adopted under ADR 0018. Link the discussion Issue and merge PR when they exist. If not, use git history as the record.

Context

This ADR explains why we automate publishing a container image from Git, what problem that solves for newcomers and operators, and how far automation goes in this repository (registry delivery, not full production rollout).

What problem are we solving?

Before this decision, the service could be built and tested locally and in CI (continuous integration), but there was no single, repeatable path that said: “every accepted change on the integration branch produces the same container image artifact in a registry that others can pull.” That gap matters because:

CI vs CD (for beginners)

Continuous integration (CI) answers: “Is this code in a good state?” — tests, lint, types, generated docs, and related checks run on a clean machine (for example GitHub Actions) when you open a pull request or push to the integration branch. CI does not, by itself, put your app on the internet.

Continuous delivery (CD) usually means: “After CI passes, deliver a deployable artifact.” In practice that often means building a Docker image and pushing it to a container registry so any environment authorized to pull can run that exact image. Some teams also automate the next step (deploy to staging/production) in the same pipeline; this repository stops at registry delivery unless you add external steps yourself.

Why stop at the registry? Hosting (VM, managed service, or your deployment platform) needs secrets, database URLs, networking, and policies that are specific to your infrastructure. Those belong in the deployment platform or runbooks, not hard-coded in a generic open-source workflow. This ADR still delivers a concrete, automatable outcome: a published image per successful pipeline.

Why GitHub Container Registry (GHCR)?

GHCR (ghcr.io) is GitHub’s container registry. It fits this project because:

How this relates to ADR 0015

ADR 0015 defines what goes into the image (Dockerfile layout, entrypoint). This ADR defines automation that builds that image in CI and pushes it to GHCR after the same quality gates that protect merges. It does not replace local development with make run; it complements packaging for downstream environments.

Decision

Scope

Alternatives considered

  1. Manual docker build and docker push only
    • Pros: no CI minutes; full manual control.
    • Cons: easy to forget; inconsistent tags; no guarantee the image matches a commit that passed CI. Rejected as the default for the integration branch.
  2. A separate workflow file for CD only
    • Pros: clearer separation of “CI” vs “CD” in the GitHub Actions UI.
    • Cons: duplicated trigger conditions; a single workflow with needs keeps ordering obvious. We keep CD in ci.yml for simplicity.
  3. Deploy to a host (SSH or remote API) in the same job
    • Pros: end-to-end automation from push to running service.
    • Cons: requires secrets and target infrastructure; not generic. Deferred until a concrete environment exists.

Consequences

Positive

Trade-offs

Compatibility and migration

Validation

References

Page history

Date Change Author
Added Page history section (repository baseline). Ivan Boyarkin