Skip to content

How to deploy an app

Deploying is automatic when a commit is made to a project's main branch and the CI/CD pipeline is triggered.

The pipeline builds and versions the app image, signs and pushes the image to GitHub's package registry, and then updates a Helm chart repository with the new version. If cdn_enabled=true, the pipeline also rewrites static asset URLs in the image to use a CDN, and uploads those assets to a CDN.

1. Checkout & Versioning

  1. Source repo is checked out.
  2. semantic-release inspects commits and determines if this is a formal release.
  3. App version is computed:
    • Release uses the semantic-release version.
    • Release candidate (RC) generates a timestamp-based RC version.

2. Build Image

  1. App image is built (not pushed).
  2. Image is tagged with:
    • the computed version
    • stable (for releases)
    • latest
3. Optional: CDN Rewrite + Upload

If cdn_enabled=true:

3a. Validate CDN configuration

  • Ensures required CDN variables and Azure token exist.

3b. Extract static files

  • Creates a temporary container from the built image.
  • Copies /usr/share/nginx/html into site/.

3c. Compute CDN asset version

  • Collects files matching configured extensions (css, js, png, etc.).
  • Hashes all matching files produces a CDN asset version.
  • This version becomes part of the CDN path.

3d. Rewrite HTML asset URLs

  • All <img>, <script>, <link> references that match the extensions are rewritten to:

    <CDN_BASE_URL>/cdn/bcit-ltc/<app>/<asset_version>/<assets>

3e. Commit rewritten files back into the container

  • Copies rewritten files back into the runtime image.
  • Commits the container final app image (with CDN references baked in).

3f. Upload assets to CDN

  • Checks asset hash against the CDN folders to determine if asset version already exists.

  • If yes skip upload.

  • If no upload assets.

4. Push & Sign

  • All computed image tags are pushed to GHCR.
  • The workflow resolves their digests.
  • Each unique digest is signed using cosign.

5. Helm Chart Update

  • A GitHub App token is generated.
  • A remote workflow in the helm-charts repo is triggered to bump the chart version to match the new image version.

Visual of the workflow

flowchart TD
  A[Commit] --> B[Checkout Repo]
  B --> C[Run semantic-release]
  C --> D[Compute Version]
  D --> E[Build Container Image]
  E --> F[Generate Tags & Metadata]
  F --> G{CDN Enabled?}

  G -->|No| X1[Skip CDN Steps]

  subgraph CDNENABLED[CDN Enabled]
    direction TB
    H1[Validate CDN Config]
    H1 --> I1[Extract Static Files → site/]
    I1 --> J1[Compute CDN Asset Version]
    J1 --> K1[Rewrite HTML Asset URLs]
    K1 --> L1[Commit Rewritten Files Into Image]
    L1 --> M1{Assets Already On CDN?}

    M1 -->|Yes| N1[Skip CDN Upload]
    M1 -->|No| O1[Upload Assets to CDN]

    %% Both Yes/No outcomes converge to Normalize Tags
    N1 --> P1[Normalize Image Tags]
    O1 --> P1
  end

  %% Connect the decision to the subgraph start
  G -->|Yes| H1

  %% --- Unified downstream path for BOTH branches ---
  X1 --> Q[Push Image Tags]
  P1 --> Q

  Q --> R[Sign Digests with Cosign]
  R --> S[Trigger Helm Chart Bump]
  S --> END[End]