Skip to content

feat(ka): consolidate canonical runtime #791

feat(ka): consolidate canonical runtime

feat(ka): consolidate canonical runtime #791

Workflow file for this run

name: Deploy
on:
push:
branches: [ main ]
tags:
- 'v*'
workflow_dispatch:
inputs:
deploy_production:
description: "Run production deployment steps"
required: false
default: false
type: boolean
permissions:
contents: read
packages: write
jobs:
build-and-test:
name: Build and Test
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@34e114876b0b11c390a56381ad16ebd13914f8d5 # v4
- name: Set up Python
uses: actions/setup-python@a26af69be951a213d495a4c3e4e4022e16d87065 # v5
with:
python-version: '3.11'
- name: Set up Node.js
uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 # v4
with:
node-version: '24'
- name: Install Python dependencies
run: |
python -m pip install --require-hashes -r requirements.lock
- name: Install Node dependencies
run: |
cd frontend
npm ci
- name: Run deterministic startup precheck gate
run: |
python scripts/runtime_precheck.py --strict --skip-ports --allow-env-from-process --json-report reports/runtime_precheck_report_deploy.json
env:
FLASK_ENV: "testing"
SESSION_SECRET: "ci-session-secret"
DATABASE_URL: "sqlite:///:memory:"
OPENAI_API_KEY: "mock-key-for-ci"
- name: Build frontend
run: |
cd frontend
npm run build
- name: Run smoke bootstrap check
run: |
python scripts/test_smoke.py
- name: Validate docs references
run: |
python scripts/verify_docs_references.py
- name: Validate SQLite/Postgres schema parity
run: |
python scripts/validate_schema_parity.py --report reports/schema_parity_report_deploy.json
- name: Run tests
run: |
python -m pytest tests/ -v --no-cov
env:
PYTHONPATH: "."
DATABASE_URL: "sqlite:///:memory:"
OPENAI_API_KEY: "mock-key-for-ci"
FLASK_ENV: "testing"
SESSION_SECRET: "ci-session-secret"
SECRET_KEY: "ci-test-secret-key"
JWT_SECRET_KEY: "ci-test-jwt-secret"
- name: Run phase 3 integrity + crash controls regression
run: |
python -m pytest -q --no-cov tests/unit/test_phase3_integrity_crash_controls.py
env:
PYTHONPATH: "."
DATABASE_URL: "sqlite:///:memory:"
OPENAI_API_KEY: "mock-key-for-ci"
FLASK_ENV: "testing"
SESSION_SECRET: "ci-session-secret"
SECRET_KEY: "ci-test-secret-key"
- name: Verify installer artifact integrity
run: |
python scripts/verify_installer_integrity.py --report reports/installer_integrity_report_deploy.json
- name: Check crash reporting configuration
id: crash-reporting-config
env:
SENTRY_DSN: ${{ secrets.SENTRY_DSN }}
run: |
if [ -n "$SENTRY_DSN" ]; then
echo "configured=true" >> "$GITHUB_OUTPUT"
else
echo "configured=false" >> "$GITHUB_OUTPUT"
fi
- name: Verify crash reporting provider pipeline (optional)
if: steps.crash-reporting-config.outputs.configured == 'true'
env:
SENTRY_DSN: ${{ secrets.SENTRY_DSN }}
FLASK_ENV: "production"
APP_VERSION: "deploy-pipeline"
run: |
python scripts/send_sentry_test_event.py --message "DataLogicEngine deploy crash-reporting probe" --tag source=deploy --tag workflow=deploy
docker-build:
name: Build Docker Images
runs-on: ubuntu-latest
needs: build-and-test
if: |
(github.event_name == 'push' && github.ref == 'refs/heads/main') ||
github.event_name == 'workflow_dispatch'
env:
REGISTRY_IMAGE: ghcr.io/${{ github.repository_owner }}/datalogicengine
GHCR_PUSH_ENABLED: ${{ secrets.GHCR_PAT != '' }}
steps:
- uses: actions/checkout@34e114876b0b11c390a56381ad16ebd13914f8d5 # v4
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@8d2750c68a42422c14e847fe6c8ac0403b4cbd6f # v3
- name: Log in to Container Registry
if: env.GHCR_PUSH_ENABLED == 'true'
uses: docker/login-action@c94ce9fb468520275223c153574b00df6fe4bcc9 # v3
with:
registry: ghcr.io
username: ${{ github.repository_owner }}
password: ${{ secrets.GHCR_PAT }}
- name: Extract metadata
id: meta
uses: docker/metadata-action@c299e40c65443455700f0fdfc63efafe5b349051 # v5
with:
images: ${{ env.REGISTRY_IMAGE }}
tags: |
type=ref,event=branch
type=semver,pattern={{version}}
type=semver,pattern={{major}}.{{minor}}
type=sha
- name: Build Docker image (push when GHCR_PAT is set)
uses: docker/build-push-action@10e90e3645eae34f1e60eeb005ba3a3d33f178e8 # v6
with:
context: .
file: Dockerfile.cloud
push: ${{ env.GHCR_PUSH_ENABLED == 'true' }}
tags: ${{ steps.meta.outputs.tags }}
labels: ${{ steps.meta.outputs.labels }}
cache-from: type=gha
cache-to: type=gha,mode=max
deploy-config:
name: Deployment Config Gate
runs-on: ubuntu-latest
needs: docker-build
if: github.event_name == 'workflow_dispatch' && inputs.deploy_production == true
outputs:
healthcheck_configured: ${{ steps.validate.outputs.healthcheck_configured }}
steps:
- name: Validate deployment variables
id: validate
env:
DEPLOY_COMMAND: ${{ vars.DEPLOY_COMMAND }}
HEALTHCHECK_URL: ${{ vars.PRODUCTION_HEALTHCHECK_URL }}
run: |
if [ -z "$DEPLOY_COMMAND" ]; then
echo "::error::Missing repository variable DEPLOY_COMMAND."
echo "::error::Set it in Settings > Secrets and variables > Actions > Variables."
exit 1
fi
if [ -z "$HEALTHCHECK_URL" ]; then
echo "::warning::PRODUCTION_HEALTHCHECK_URL is not configured; health check will be skipped."
echo "healthcheck_configured=false" >> "$GITHUB_OUTPUT"
else
echo "healthcheck_configured=true" >> "$GITHUB_OUTPUT"
fi
deploy-production:
name: Deploy to Production
runs-on: ubuntu-latest
needs: deploy-config
if: github.event_name == 'workflow_dispatch' && inputs.deploy_production == true
environment:
name: production
url: https://datalogicengine.com
steps:
- uses: actions/checkout@34e114876b0b11c390a56381ad16ebd13914f8d5 # v4
- name: Deploy to production
env:
DEPLOY_COMMAND: ${{ vars.DEPLOY_COMMAND }}
run: |
bash -lc "$DEPLOY_COMMAND"
- name: Production health check
if: needs.deploy-config.outputs.healthcheck_configured == 'true'
env:
HEALTHCHECK_URL: ${{ vars.PRODUCTION_HEALTHCHECK_URL }}
run: |
curl --fail --silent --show-error --retry 5 --retry-delay 5 --retry-connrefused "$HEALTHCHECK_URL"
- name: Notify deployment status
if: always()
run: |
echo "Send notification about deployment status"
echo "Status: ${{ job.status }}"