From 36d0c88cee10b93fe7d9001537358098aa64dc38 Mon Sep 17 00:00:00 2001 From: Andrew Stoltz Date: Sun, 17 May 2026 23:17:38 -0500 Subject: [PATCH] feat(chat): add public twin ingress --- apps/fc-chat/fc-chat.yaml | 38 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 38 insertions(+) diff --git a/apps/fc-chat/fc-chat.yaml b/apps/fc-chat/fc-chat.yaml index a4de518..572210e 100644 --- a/apps/fc-chat/fc-chat.yaml +++ b/apps/fc-chat/fc-chat.yaml @@ -30,3 +30,41 @@ spec: port: 80 tls: secretName: chat-web-tls +--- +# Public host profile marker. The app treats this header as authoritative for +# the public twin, while the internal chat.iamworkin.lan route does not attach +# it and keeps the operator-oriented UI. +apiVersion: traefik.io/v1alpha1 +kind: Middleware +metadata: + name: chat-public-profile-header + namespace: fc-chat +spec: + headers: + customRequestHeaders: + X-FC-Chat-Host-Profile: "public" +--- +# Public Cloudflare-fronted twin for the anonymous chat surface. Operator +# paths are intentionally absent from the allowlist below, so /admin, +# /operator, /console, /ops, /api/operator, and /operatorhub miss this route +# and return Traefik 404 before reaching the pod. Operator action still needed: +# create/verify Cloudflare DNS chat.flowercore.io -> public Traefik endpoint +# and mirror the cf-origin-flowercore-io TLS secret into namespace fc-chat. +apiVersion: traefik.io/v1alpha1 +kind: IngressRoute +metadata: + name: chat-web-public + namespace: fc-chat +spec: + entryPoints: + - websecure + routes: + - match: Host(`chat.flowercore.io`) && (Path(`/`) || Path(`/chat`) || PathPrefix(`/_blazor`) || PathPrefix(`/_framework`) || PathPrefix(`/_content`) || PathPrefix(`/avatars`) || PathPrefix(`/css`) || PathPrefix(`/js`) || PathPrefix(`/favicon`) || PathPrefix(`/chathub`)) && (Method(`GET`) || Method(`HEAD`) || Method(`POST`) || Method(`OPTIONS`)) + kind: Rule + middlewares: + - name: chat-public-profile-header + services: + - name: chat-web + port: 80 + tls: + secretName: cf-origin-flowercore-io