# bp-catalyst-platform — Catalyst Blueprint #13 of 13. The umbrella
# Blueprint that brings up the Catalyst control plane: console, marketplace,
# admin, catalog-svc, projector, provisioning, environment-controller,
# blueprint-controller, billing.
#
# Per docs/ARCHITECTURE.md §11 (Catalyst-on-Catalyst): once this is Ready,
# the Sovereign is fully self-sufficient — sovereign-admin can log into
# console.${SOVEREIGN_FQDN} and proceed with Phase 2 day-1 setup.
#
# Wrapper chart: products/catalyst/chart/

---
apiVersion: v1
kind: Namespace
metadata:
  name: catalyst-system
  labels:
    catalyst.openova.io/sovereign: ${SOVEREIGN_FQDN}
---
apiVersion: source.toolkit.fluxcd.io/v1beta2
kind: HelmRepository
metadata:
  name: bp-catalyst-platform
  namespace: flux-system
spec:
  type: oci
  interval: 15m
  url: oci://ghcr.io/openova-io
  secretRef:
    name: ghcr-pull
---
apiVersion: helm.toolkit.fluxcd.io/v2
kind: HelmRelease
metadata:
  name: bp-catalyst-platform
  namespace: flux-system
spec:
  interval: 15m
  releaseName: catalyst-platform
  targetNamespace: catalyst-system
  dependsOn:
    - name: bp-gitea
    # bp-gateway-api (issue #503): umbrella chart ships catalyst-ui +
    # catalyst-api HTTPRoute templates; gateway.networking.k8s.io/v1
    # CRDs must be registered first.
    - name: bp-gateway-api
    # bp-keycloak + bp-cnpg (issue #512): the catalyst-platform umbrella
    # post-install Jobs bootstrap OIDC clients in Keycloak and seed
    # PostgreSQL schemas for catalog-svc / projector / billing /
    # provisioning. Both Keycloak and cnpg take 5+ minutes to reach Ready
    # on a fresh Sovereign — without an explicit dep, the umbrella's
    # hook starts before they're warm and times out at 15m.
    # Phase-8a-preflight otech16 (2026-05-02): adding bp-keycloak +
    # bp-cnpg here makes Flux wait for both Ready=True before starting
    # the umbrella install, eliminating the race.
    - name: bp-keycloak
    - name: bp-cnpg
  chart:
    spec:
      chart: bp-catalyst-platform
      # 1.4.0 (issue #827): adds per-zone wildcard Certificate template.
      # When `parentZones` is populated the chart renders one
      # cert-manager.io/v1.Certificate per zone in kube-system; the
      # Cilium Gateway listeners reference the per-zone Secrets. When
      # `parentZones` is empty (legacy single-zone Sovereign) the chart
      # falls back to a single Certificate covering `*.<sovereignFQDN>`
      # so existing provisioning paths keep working.
      # 1.4.1 (PR #839): RBAC dual-mode render fix (Helm + Kustomize).
      # 1.4.2 (PR #841): POWERDNS env literal (no envsubst-mid-render).
      # 1.4.3 (issue #859): auto-provision sme-pg CNPG Cluster +
      # sme-secrets when ingress.marketplace.enabled=true so SME
      # services land Ready on a fresh Sovereign without hand-rolled
      # SealedSecrets. Catalyst-Zero (contabo) keeps its pre-existing
      # clusters/contabo-mkt/apps/sme/data/* manifests — those are
      # outside templates/kustomization.yaml's resource list so the
      # contabo Kustomize-mode build is unaffected.
      # 1.4.4 (issue #861): deploy FerretDB in `sme` ns + cross-ns
      # CiliumNetworkPolicy from sme → valkey. Unblocks the 4 SME
      # services (catalog, tenant, domain, provisioning) that pin to
      # ferretdb.sme.svc.cluster.local for the MongoDB wire and the 2
      # services (auth, gateway) that pin to valkey for session/state.
      # cnpg-cluster.yaml extended to bootstrap sme_documents (FerretDB
      # backing DB) alongside sme_billing.
      # 1.4.5 (issue #863): mirror bp-valkey's auto-generated auth
      # password from `valkey/valkey` Secret into `sme/sme-valkey-auth`
      # via Helm lookup, and wire VALKEY_PASSWORD into auth + gateway
      # Deployments. Clears the NOAUTH HELLO crashloop that started
      # appearing after 1.4.4 made cross-ns Valkey reachable.
      # 1.4.6 (issue #863 follow-up): rebuild chart artifact to bundle
      # the rebuilt services-auth + services-gateway image (SHA fa4395f)
      # that contains the ConnectValkeyWithAuth Go change. 1.4.5 shipped
      # with the OLD image SHA baked in due to a race between the
      # blueprint-release pipeline and the services-build deploy step.
      # 1.4.7 (issue #866): mirror the gitea-admin password into
      # `sme/provisioning-github-token` so the last 1/13 SME pod
      # (provisioning) reaches Running 1/1 on a fresh Sovereign,
      # completing the SME stack 12/13 → 13/13. Same lookup-and-mirror
      # pattern as valkey-cross-ns-secret.yaml (#863).
      # 1.4.8 (issue #868): fix marketplace UI PIN-signin — /api/*
      # HTTPRoute now backendRefs sme/gateway:8080 (cross-namespace,
      # authorised by ReferenceGrant). The previous catalyst-system/
      # marketplace-api Service had zero backing Pods, so every signin
      # POST 503'd at the gateway. Pairs with services-auth route alias
      # /auth/send-pin → SendMagicLink (and /auth/verify-pin →
      # VerifyMagicLink) so the UI's PIN-naming reaches the existing
      # backend handler.
      version: 1.4.11
      sourceRef:
        kind: HelmRepository
        name: bp-catalyst-platform
        namespace: flux-system
  # Event-driven install: umbrella chart deploys ~10 Catalyst services
  # (console, marketplace, admin, catalog-svc, projector, provisioning,
  # environment-controller, blueprint-controller, billing). Inter-service
  # readiness via OTel/NATS subjects is multi-minute and not Helm's
  # concern. Replaces PR #221 spec.timeout: 15m.
  install:
    disableWait: true
    timeout: 15m
    remediation:
      retries: 3
  upgrade:
    disableWait: true
    timeout: 15m
    remediation:
      retries: 3
  # Per-Sovereign overrides for the umbrella — sovereign-FQDN-derived hostnames
  # for console/admin/api. All chart-level Catalyst service config (image refs,
  # OTel endpoints, NATS subjects) lives in products/catalyst/chart/values.yaml.
  values:
    global:
      sovereignFQDN: ${SOVEREIGN_FQDN}
    ingress:
      hosts:
        console:
          host: console.${SOVEREIGN_FQDN}
        admin:
          host: admin.${SOVEREIGN_FQDN}
        marketplace:
          host: marketplace.${SOVEREIGN_FQDN}
        api:
          host: api.${SOVEREIGN_FQDN}
      # Marketplace mode (issue #710). Toggle to true via envsubst
      # MARKETPLACE_ENABLED in the per-Sovereign overlay (catalyst-api
      # writes this when the wizard's "Enable Marketplace" component is
      # checked). When true, bp-catalyst-platform 1.3.0+ renders the
      # marketplace + tenant-wildcard HTTPRoutes and the cross-namespace
      # ReferenceGrant.
      marketplace:
        enabled: ${MARKETPLACE_ENABLED:-false}
    # ─── Multi-zone parent domains (issue #827, parent epic #825) ──────
    # One wildcard Certificate per parent zone, rendered by chart 1.4.0+
    # into kube-system. Each cert renews independently; a stalled
    # DNS-01 challenge on one zone never blocks another zone's renewal.
    # Source of truth is the same ${PARENT_DOMAINS_YAML} variable used
    # by bootstrap-kit slot 11 (bp-powerdns) so the two slots stay in
    # lockstep on what the Sovereign considers a parent zone.
    # When the operator brings only one parent domain (default
    # zero-touch flow), cloud-init pre-renders this variable to a
    # single-entry array derived from ${sovereign_fqdn}.
    parentZones: ${PARENT_DOMAINS_YAML}
