Skip to main content

Production Setup

This guide covers the minimum configuration required to deploy Hephaestus in production. It assumes you are familiar with Docker Compose or Kubernetes and have access to the protected secrets managed by TUM.

Platform overview

The production stack consists of:

  • Application server (Spring Boot)
  • Intelligence service (TypeScript + Hono)
  • Webhook ingest (Hono/TypeScript → NATS JetStream)
  • React webapp (served via nginx)
  • PostgreSQL 16
  • Keycloak (with GitHub and optional GitLab identity providers)

Environment variables

Set the following secrets before starting the stack:

VariablePurpose
WEBHOOK_SECRETHMAC secret for GitHub and GitLab webhooks (prefer SHA-256; e.g., openssl rand -hex 32)
KEYCLOAK_GITHUB_CLIENT_IDGitHub OAuth app client ID
KEYCLOAK_GITHUB_CLIENT_SECRETGitHub OAuth app client secret
KEYCLOAK_GITHUB_ADMIN_USERNAMEGitHub username that should receive Keycloak admin rights
KC_BOOTSTRAP_ADMIN_USERNAMEKeycloak bootstrap admin username
KC_BOOTSTRAP_ADMIN_PASSWORDKeycloak bootstrap admin password (openssl rand -base64 32)
KEYCLOAK_HEPHAESTUS_CONFIDENTIAL_CLIENT_SECRETSecret used by the app server to call Keycloak
SLACK_BOT_TOKENOptional: Slack bot token for notifications
SLACK_SIGNING_SECRETOptional: Slack signing secret for webhook verification
LEGAL_PROFILESelects a bundled imprint/privacy profile. Use tumaet only for the canonical AET deployment; self-hosters leave empty and mount /legal-overrides/. See Legal Pages.

GitHub integration

Hephaestus can connect to GitHub using either a Personal Access Token (PAT) or a GitHub App:

  • Personal Access Token: Simpler to set up. Configure tokens through the workspace UI after deployment. No additional environment variables required.
  • GitHub App (optional): Provides more granular permissions and better rate limits. If using a GitHub App, set:
    • GH_APP_ID: Your GitHub App ID
    • GH_APP_PRIVATE_KEY: Your GitHub App private key (PEM format)
    • GH_APP_PRIVATE_KEY_LOCATION: Alternative path to private key file (optional)
    • GH_APP_INSTALLATION_URL: Install URL shown in the workspace creation wizard

The application works with either approach. If GitHub App credentials are not provided (defaults to GH_APP_ID=0), workspaces will use Personal Access Tokens instead.

GitLab rollout bundle

GitLab login, GitLab workspaces, webhook auto-registration, and practice review are not independent toggles. Treat the following as a rollout bundle and enable them together when rolling out GitLab practice review:

VariablePurpose
KEYCLOAK_GITLAB_ENABLEDEnables the GitLab identity provider in Keycloak
KEYCLOAK_GITLAB_CLIENT_IDGitLab OAuth application client ID
KEYCLOAK_GITLAB_CLIENT_SECRETGitLab OAuth application client secret
KEYCLOAK_GITLAB_BASE_URLBase URL of the GitLab instance used for login and default workspace server selection
KEYCLOAK_GITLAB_ADMIN_USERNAMEOptional GitLab username that should receive Keycloak admin rights on first login
GITLAB_ENABLEDEnables server-side GitLab beans in the application server
GITLAB_WORKSPACE_CREATIONEnables GitLab workspace creation in the UI and API
WEBHOOK_SECRETShared secret used for GitLab webhook verification and auto-registration
WEBHOOK_EXTERNAL_URLPublic webhook base URL registered on GitLab

Create the GitLab OAuth application with these settings:

  • Redirect URI: https://<hostname>/keycloak/realms/hephaestus/broker/gitlab-lrz/endpoint
  • Scopes: openid, profile, email
  • Confidential client: enabled

Practice review rollout bundle

Practice review is not enabled by a single flag. The following settings must be aligned:

VariablePurpose
PRACTICE_REVIEW_FOR_ALLEnables the feature flag and the detection gate for all users
PRACTICE_REVIEW_SKIP_DRAFTSSkips draft PRs and draft merge requests
PRACTICE_REVIEW_DELIVER_TO_MERGEDAllows delivery after merge
PRACTICE_REVIEW_COOLDOWN_MINUTESMinimum delay between repeated reviews of the same PR/MR
PRACTICE_REVIEW_APP_BASE_URLFooter link in review comments
SANDBOX_ENABLEDEnables the Docker sandbox used by the coding agent
AGENT_NATS_ENABLEDEnables the agent job queue and executor
GIT_CHECKOUT_ENABLEDEnables local repo checkout and bind-mount into agent containers
NATS_ENABLEDEnables webhook-driven sync consumption
NATS_DURABLE_CONSUMER_NAMEDurable consumer name for sync processing

SANDBOX_ENABLED, AGENT_NATS_ENABLED, GIT_CHECKOUT_ENABLED, and NATS_ENABLED must be true together for practice review. Anything else is a half-configured deployment.

Rollout tiers

Use the same variables differently across environments:

EnvironmentIntended scope
PreviewLimited by default. Keep GitLab login, GitLab workspaces, sandbox, git checkout, and agent job execution disabled unless preview is explicitly being used as rollout validation.
StagingUses the production compose files, but should still be a controlled rollout. Start by enabling GitLab login and GitLab workspace creation first. Only enable SANDBOX_ENABLED, AGENT_NATS_ENABLED, GIT_CHECKOUT_ENABLED, and NATS_ENABLED when staging is intentionally validating practice review execution.
ProductionFull rollout only after staging has validated the exact same bundle.

Staging and production both use the production compose files. The difference should come from the .env values, not from a different compose topology.

AI model configuration

The intelligence-service model selection and the sandboxed practice-review proxy are two different paths.

For the intelligence-service:

VariablePurpose
MODEL_NAMEProvider-qualified model name such as openai:gpt-4o or azure:gpt-5.4-mini
OPENAI_API_KEYRequired when MODEL_NAME starts with openai:
AZURE_RESOURCE_NAMERequired when MODEL_NAME starts with azure:
AZURE_API_KEYRequired when MODEL_NAME starts with azure:

For Azure-backed practice review in the application server:

VariablePurpose
LLM_PROXY_AZURE_OPENAI_URLAzure OpenAI resource URL used by the dedicated Azure proxy route
LLM_PROXY_AZURE_OPENAI_AUTH_HEADERUsually api-key
LLM_PROXY_AZURE_OPENAI_USE_BEARERUsually false for Azure OpenAI

The generic LLM_PROXY_OPENAI_* settings only affect the OpenAI-compatible proxy route. The sandboxed Pi agent uses the dedicated Azure route when configured for Azure OpenAI.

Webhook secret: Set WEBHOOK_SECRET to the secret configured on your GitHub and GitLab webhooks. Prefer SHA-256 (X-Hub-Signature-256) and generate with openssl rand -hex 32 (base64 also works).

Data sync and backfill

The sync scheduler fetches recent GitHub activity (issues, PRs, reviews) for monitored repositories. Backfill optionally syncs historical data in batches to avoid rate limit exhaustion.

VariableDefaultPurpose
MONITORING_RUN_ON_STARTUPtrueRun initial sync when application starts
MONITORING_TIMEFRAME7Days of recent activity to sync each cycle
MONITORING_SYNC_CRON0 0 * * * *Cron schedule for sync (hourly by default)
MONITORING_SYNC_COOLDOWN_IN_MINUTES60Minimum gap between syncs per repository
MONITORING_BACKFILL_ENABLEDtrueEnable historical data backfill
MONITORING_BACKFILL_BATCH_SIZE50Issues/PRs per backfill batch
MONITORING_BACKFILL_RATE_LIMIT_THRESHOLD500Skip backfill if rate limit below this
MONITORING_BACKFILL_INTERVAL_SECONDS60Interval between backfill batches

Backfill behavior: After recent sync completes, backfill works backwards from the highest issue number, syncing in small batches. It pauses when rate limits drop below the threshold and resumes on the next cycle. Progress is checkpointed per repository.

Deployment steps

  1. Provision infrastructure: Ensure PostgreSQL, Redis (if used), and storage volumes are ready.
  2. Configure Keycloak:
    • Import the keycloak-hephaestus-realm-example-config.json from the repository.
    • Copy server/application-server/.env.example to server/application-server/.env, then populate KEYCLOAK_GITHUB_CLIENT_ID, KEYCLOAK_GITHUB_CLIENT_SECRET, KEYCLOAK_GITHUB_ADMIN_USERNAME, and KEYCLOAK_HEPHAESTUS_CONFIDENTIAL_CLIENT_SECRET so the realm import can resolve them using Keycloak's environment variable placeholders.
    • Confirm the GitHub identity provider requests the user:email scopes and disable username/password login flows to keep authentication SSO-only.
    • If rolling out GitLab login, also configure the GitLab identity provider and apply the manual Keycloak adjustments for first broker login, automatic account linking, relaxed name validation, and clock skew tolerance.
  3. Bootstrap secrets: Load environment variables into your secret manager or .env files consumed by Docker/Kubernetes.
  4. Deploy services: Use the provided Compose files (docker/compose.app.yaml, docker/compose.core.yaml, docker/compose.proxy.yaml) or your Kubernetes manifests.
  5. Run database migrations: The application server runs Liquibase migrations on startup; monitor logs to confirm success.
  6. Verify integrations:
    • Sign in via GitHub with the account configured in KEYCLOAK_GITHUB_ADMIN_USERNAME and confirm it lands in Keycloak with both the admin realm role and the realm-managementrealm-admin client role automatically applied.
    • Verify that the super admin user can access workspace admin endpoints for workspaces where they have membership (they are automatically elevated to workspace ADMIN level for those workspaces).
    • Trigger a test webhook from GitHub or GitLab to validate the ingest pipeline.
    • Verify that GITLAB_ENABLED, GITLAB_WORKSPACE_CREATION, SANDBOX_ENABLED, AGENT_NATS_ENABLED, GIT_CHECKOUT_ENABLED, and NATS_ENABLED are all present in the deployed environment before testing GitLab practice review.
    • Open /imprint and /privacy. If the red "not configured" banner is shown, configure a legal profile or overrides before opening the deployment to end users — serving the built-in disclaimer is a § 5 DDG / Art. 13 GDPR violation.

Global admin privileges

Users configured in KEYCLOAK_GITHUB_ADMIN_USERNAME receive the admin realm role automatically on first GitHub login. This grants them:

  • Full Keycloak admin console access (realm-managementrealm-admin client role)
  • Automatic workspace ADMIN privileges for workspaces where they have membership (they are auto-elevated to workspace ADMIN level)
  • Ability to manage workspace settings, members, and repositories in their member workspaces
  • Cannot perform OWNER-only operations (e.g., workspace ownership transfer) unless explicitly granted the OWNER role in that workspace
  • Must have workspace membership (any role: OWNER, ADMIN, or MEMBER) to access the workspace

This allows platform administrators to troubleshoot and manage workspaces where they are members, with automatic admin privileges, without needing explicit ADMIN role assignment in the database.

Operational tips

  • Monitor services with the central Prometheus/Loki stack; ensure trace IDs appear in logs.
  • Schedule regular backups for PostgreSQL and Keycloak.
  • Review weekly leaderboard Slack posts to ensure the automation is active.
  • Preview deployments do not currently represent the full GitLab practice-review rollout unless they are explicitly wired with the same GitLab IdP, sandbox, git checkout, and agent NATS settings.

Support

Contact the Hephaestus core team if you need to rotate secrets or migrate infrastructure. Document any deviations from this checklist in the deployment runbook.