Repository navigation
Continuous integration & Build Valudation
How the CI GitHub Actions workflow validates every change before production Deploy can run.
| Workflow file | .github/workflows/ci.yml |
| Workflow name | CI |
| Runs on | Every pull request, and every push to main
|
| Job | Single job validate on ubuntu-latest
|
| Permissions |
contents: read only (no AWS, no OIDC write) |
| Concurrency | Group ci-${{ github.ref }}; cancels in-progress runs on PRs only (main pushes are not cancelled mid-flight) |
Companion pages: Continuous deployment, Build issues, Deployment issues.
CI is the quality and security gate for the monorepo: Python data jobs, browser JS, Terraform, the arm64 Lambda image, and GitHub Actions / Dockerfile checks. A failed CI run never deploys. Production Deploy only starts after a successful CI on a push to main (or a manual Deploy from main — see Continuous deployment).
on:
pull_request:
push:
branches: [main]- Pull request — validates the merge result of the PR branch. Concurrent PR runs for the same ref cancel older ones so you only wait on the latest commit.
-
Push to
main— re-validates what landed. This is the signal Deploy watches viaworkflow_run(Deploy does not run on PR CI success alone).
There is no workflow_dispatch on CI; you push or open a PR to run it.
Third-party actions are pinned to full commit SHAs (version tags only in comments), which reduces supply-chain drift.
| Step | Tool | Version / notes |
|---|---|---|
| Checkout | actions/checkout |
Credentials not persisted (persist-credentials: false) |
| Python | actions/setup-python |
3.12, pip cache from services/data-jobs/requirements-jobs.txt
|
| Node | actions/setup-node |
22 (syntax-check only for the static site) |
| Terraform | hashicorp/setup-terraform |
CLI 1.16.5 |
| Docker | QEMU + Buildx |
arm64 (matches Lambda Graviton / linux/arm64 image) |
Python packages installed for the job: deps from requirements-jobs.txt + requirements-test.txt, plus ruff and pip-audit.
working-directory: services/data-jobs
ruff check src tests scripts
Style and common-bug checks for collectors, jobs app code, tests, and helper scripts.
pytest -q
Unit / fixture tests under services/data-jobs (quiet mode). Failures block the green check.
pip-audit -r services/data-jobs/requirements-jobs.txt
pip-audit -r services/data-jobs/requirements-test.txt
Known vulnerability scan on runtime and test requirement locks. A finding fails the job until deps are upgraded or explicitly addressed.
node --check apps/web/app.js
No frontend bundler: the site is static HTML/CSS/JS. This only parses apps/web/app.js for syntax errors (no browser runtime tests in CI today).
working-directory: infra/terraform
terraform fmt -check -recursive
terraform init -backend=false
terraform validate
-
fmt -check— fails if.tffiles are not formatted (no auto-rewrite in CI). -
init -backend=false— downloads providers / modules without talking to the S3 state backend (no AWS creds on CI). -
validate— configuration graph is valid. This is not aterraform planagainst live state.
docker buildx build --file infra/docker/Dockerfile --platform linux/arm64 --load -t investor-dashboard-jobs:ci .
Proves the jobs image builds for the architecture Deploy will push to ECR. CI loads the image locally (--load); it does not push to ECR. Publish happens only in Deploy.
bridgecrewio/checkov-action
directory: .
framework: terraform,dockerfile,github_actions
quiet: true
Static analysis for risky Terraform, Dockerfile, and Actions patterns. Quiet mode keeps logs shorter; findings still fail the job.
| Not in CI | Where it happens instead |
|---|---|
| Assume AWS roles / OIDC | Continuous deployment only |
terraform plan / apply against real state |
Deploy (and rare admin laptop applies) |
| Push images to ECR | Deploy |
| Sync the static site or invalidate CloudFront | Deploy |
| Store or read provider API keys | SSM via rotate-key.sh (Data collectors API keys) |
| Outcome | Meaning |
|---|---|
| All green on a PR | Safe to review/merge from a tooling perspective; still read the diff |
Green on main push |
Unlocks automatic Deploy if the production environment is approved |
| Red | Fix before merge; Deploy will not auto-start from a failed main CI |
Common failure themes and fixes: Build issues.
Rough local equivalents before you push:
cd services/data-jobs
ruff check src tests scripts
pytest -q
cd ../../infra/terraform
terraform fmt -check -recursive
terraform init -backend=false && terraform validate
# optional: docker buildx build --file infra/docker/Dockerfile --platform linux/arm64 -t investor-dashboard-jobs:local .You still need the GitHub Actions Checkov + pip-audit steps (or run those tools locally) for full parity.