openova/products/catalyst
e3mrah 76830d9c62
fix(catalyst): chroot — skip tenantDiscover polling, /auth/handover redirects authed user to / (#1077)
Two bugs surfaced live on console.omantel.biz on 2026-05-07.

TC-229 (P0) — chroot continuous /api/v1/tenant/discover 404 polling.
The Sovereign chroot's catalyst-api does not register the
tenant/discover endpoint (it is mother-only — only the Catalyst-Zero
apex `console.openova.io` knows about the tenant registry). The SPA's
bootstrapTenant() at app boot still ran on the chroot, returned 404,
and the SPA's React-Query layer kept re-issuing the call as the
Dashboard mounted/unmounted. 50+ HTTP 404 lines were captured during a
single Dashboard navigation. Fix: short-circuit bootstrapTenant() at
the single tenantDiscover.ts seam when DETECTED_MODE.mode ===
'sovereign'. Returns the existing 'unwired' status (no registry
available; proceed on the host's own identity), caches it so a second
call is a no-op, and never touches the network. Tenant identity on
chroot is already encoded in the session JWT (sovereign_fqdn /
deployment_id claims) so no registry payload is needed.

TC-004 (P1) — /auth/handover authenticated visit shows error page.
Fix #2 PR #1075 added the SPA-friendly handover-error page for browser
visits with no token. That branch fired even when the operator already
had a live catalyst_session cookie, so an authed user pasting the bare
/auth/handover URL saw "Handover incomplete" copy that confuses people
who are already logged in. Fix: add a three-way branch on no-token
visits — authenticated browser (302 to authHandoverRedirect, default
/dashboard), unauthenticated browser (existing 302 to handover-error
page from PR #1075), programmatic caller (existing 401 JSON contract
from auth_handover_test.go). New helper hasValidCatalystSession reads
the session token via auth.Config.ReadSessionToken (cookie / Bearer /
?access_token query — same channels RequireSession honours) and
validates it via auth.Config.ValidateToken (same path RequireSession
uses, including LocalPublicKey fallback for self-signed handover-
session JWTs). Returns false when authConfig is nil so unconfigured
Sovereigns / CI keep working unchanged.

Tests: TestAuthHandover_MissingTokenAuthedRedirectsToDashboard
(raw-JWT cookie + Bearer header), MissingTokenExpiredSessionFalls-
Through (expired session falls through to error page),
MissingTokenNoAuthConfigKeepsHTMLBranch (nil authConfig keeps the
existing branches working). Existing missing-token tests unchanged.

Files touched (per Fix Author #6 brief):
- products/catalyst/bootstrap/ui/src/shared/lib/tenantDiscover.ts
- products/catalyst/bootstrap/api/internal/handler/auth_handover.go
- products/catalyst/bootstrap/api/internal/handler/auth_handover_test.go

Co-authored-by: hatiyildiz <269457768+hatiyildiz@users.noreply.github.com>
Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-07 21:52:21 +04:00
..
bootstrap fix(catalyst): chroot — skip tenantDiscover polling, /auth/handover redirects authed user to / (#1077) 2026-05-07 21:52:21 +04:00
chart deploy: update catalyst images to 3dc9f42 2026-05-07 16:32:02 +00:00
README.md feat(consolidation): Phase 1 — move Catalyst-Zero apps + CI + manifests into public monorepo 2026-04-28 12:08:09 +02:00

OpenOva Catalyst (composite Blueprint)

The umbrella Blueprint bp-catalyst-platform — composes the Catalyst control plane.

Status: Deployed. Updated: 2026-04-28.

This product directory contains:

  • chart/ — the Helm chart that deploys Catalyst-Zero on a Kubernetes cluster (and every franchised Sovereign).
  • chart/templates/{ui,api}-deployment.yaml + service + ingress — the catalyst-ui (React SPA wizard scaffold) and catalyst-api (Go bootstrap API) workloads.
  • chart/templates/sme-services/ — 11 manifests for the legacy SME backend services + the consolidated console, admin, marketplace UI workloads (sourced from core/{console,admin,marketplace}/).
  • chart/templates/marketplace-api/ — manifests for the Go marketplace-api backend (sourced from core/marketplace-api/).
  • bootstrap/{ui,api}/ — the source code for catalyst-ui and catalyst-api (deployed via the catalyst-build CI workflow).

For the unified architecture and the wizard's target shape, see docs/PROVISIONING-PLAN.md, docs/ARCHITECTURE.md, and docs/SOVEREIGN-PROVISIONING.md.


How Catalyst-Zero is deployed today

A Flux Kustomization on the Catalyst-Zero cluster (Contabo k3s) reconciles products/catalyst/chart/templates/ from this public repo. CI workflows (.github/workflows/{catalyst,console,admin,marketplace,marketplace-api}-build.yaml) build and push images on every push to main, then the deploy step pins the image SHA into the corresponding manifest in this directory and commits back. Flux picks up the commit and rolls the deployment.

Image registry: ghcr.io/openova-io/openova/{catalyst-ui,catalyst-api,console,admin,marketplace,marketplace-api}:<sha>.

Migration status (per docs/PROVISIONING-PLAN.md)

Component Source location Image Status
catalyst-ui products/catalyst/bootstrap/ui/ ghcr.io/openova-io/openova/catalyst-ui public repo
catalyst-api products/catalyst/bootstrap/api/ ghcr.io/openova-io/openova/catalyst-api public repo
console core/console/ ghcr.io/openova-io/openova/console public repo (Phase 1)
admin core/admin/ ghcr.io/openova-io/openova/admin public repo (Phase 1)
marketplace core/marketplace/ ghcr.io/openova-io/openova/marketplace public repo (Phase 1)
marketplace-api core/marketplace-api/ ghcr.io/openova-io/openova/marketplace-api public repo (Phase 1)
sme-{auth,billing,catalog,domain,gateway,notification,provisioning,tenant} (still in openova-private/services/) ghcr.io/openova-io/openova-private/sme-* follow-up phase — source not yet moved