Red Hat Catalog Environment Promotion

Environments

Environment URL Source Deploy trigger
MR Preview GitLab Pages (/mr-{IID}) MR branch Auto on MR pipeline
Experimental images.experimental.hummingbird-project.io/<branch-name> experiment/* branch Auto on push to experiment branch
Staging images.staging.hummingbird-project.io main Auto on merge to main
Production images.redhat.com main Manual after staging deploy

Disambiguation: The in-app /experimental route is a product feature (navigation label visible to users). The “experimental environment” is an infrastructure concept (a long-lived host for off-main branches). These are independent.

Promotion Paths

Routine: staging to production

  1. MR merged to main
  2. redhat-catalog-visual-staging-reference captures live visuals on current staging
  3. deploy_redhat_catalog_staging runs automatically
  4. e2e_redhat_catalog_staging (smoke) and visual_redhat_catalog_staging (presentation diff) validate staging
  5. Approval owner clicks deploy_redhat_catalog (manual gate) after smoke and visual pass
  6. Production deploys from same commit

Exploration: experimental to staging to production

  1. Create branch experiment/<name> from main (must use exactly experiment/, not experimental/ or other prefixes — without it, no deploy triggers)
  2. Push triggers deploy_redhat_catalog_experimental automatically
  3. Branch deploys to images.experimental.hummingbird-project.io/<name>/
  4. Iterate on experimental host for days or weeks
  5. When ready: open MR from experiment/<name> to main
  6. Normal MR review, merge, then routine promotion path

Retiring an experiment

  1. Delete the experiment/<name> branch

  2. Remove the branch prefix from the experimental S3 bucket:

    aws s3 rm s3://redhat-catalog-experimental-spa/<name>/ --recursive
    
  3. Invalidate the CloudFront cache:

    aws cloudfront create-invalidation \
      --distribution-id <EXPERIMENTAL_DISTRIBUTION_ID> \
      --paths "/<name>/*"
    

Build Configuration Per Environment

The infrastructure pipeline sets these environment variables at build time:

Variable Experimental Staging Production
ASSET_PATH /<branch-name>/ / /
DPAL_USE_STAGING true true (unset, uses prod)
TRUSTARC_DATA_DOMAIN images.experimental.hummingbird-project.io images.staging.hummingbird-project.io images.redhat.com
CATALOG_API_BASE_URL (unset, uses app default) (unset, uses app default) (unset, uses prod)
CATALOG_BASE_URL (unset, uses app default) (unset, uses app default) (unset, uses prod)
HUMMINGBIRD_API_URL (unset, uses app default) (unset, uses app default) (unset, uses prod)

Infrastructure

SAM Stacks

Stack Template ResourcePrefix CatalogDomainName
redhat-catalog-prod template.yaml redhat-catalog images.redhat.com
redhat-catalog-staging template.yaml redhat-catalog-staging images.staging.hummingbird-project.io
redhat-catalog-experimental template-experimental.yaml redhat-catalog-experimental images.experimental.hummingbird-project.io

Staging uses the same template.yaml as production (single-site CloudFront distribution). Experimental uses template-experimental.yaml which adds a CloudFront Function for path-prefix SPA routing across multiple branches.

DNS

ALIAS records (images.staging/experimental.hummingbird-project.io → CloudFront) are created automatically by post_deploy.sh after each deploy.

First-time bootstrap: The SAM template creates an ACM certificate with DNS validation. The ACM validation CNAME must exist in the hummingbird-project.io Route 53 zone before the first sam deploy, or CloudFormation will wait 30 minutes and roll back. To bootstrap:

  1. Deploy with CatalogDomainName="" (uses CloudFront default domain, no cert)
  2. Create the ACM validation CNAME in Route 53 (get the value from the ACM console or aws acm describe-certificate)
  3. Redeploy with CatalogDomainName set to the real domain

After the first successful deploy, no manual DNS steps are needed.

CI/CD Variables

Set in GitLab project settings:

Variable Value
REDHAT_CATALOG_STAGING_URL https://images.staging.hummingbird-project.io

Pipeline Flow

experiment/* push:
  redhat-catalog-experimental-check
    -> deploy_redhat_catalog_experimental

MR (target main):
  redhat-catalog (build + test)
    -> redhat-catalog-browser-tests
    -> redhat-catalog-visual-mock (Playwright mock API; MR vs merge-base diff)
    -> pages (preview)

main push:
  redhat-catalog-visual-staging-reference (pre-deploy live capture)
    -> deploy_redhat_catalog_staging (auto)
      -> e2e_redhat_catalog_staging (smoke)
      -> visual_redhat_catalog_staging (post-deploy vs pre-deploy diff)
    -> deploy_redhat_catalog (manual; needs staging deploy + smoke + visual)

Visual regression details: redhat-catalog testing guide — Visual regression and e2e/visual/README.md.