diff --git a/base/lasuite/calendars-backend-deployment.yaml b/base/lasuite/calendars-backend-deployment.yaml
deleted file mode 100644
index 8913bf3..0000000
--- a/base/lasuite/calendars-backend-deployment.yaml
+++ /dev/null
@@ -1,163 +0,0 @@
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: calendars-backend
- namespace: lasuite
-spec:
- replicas: 1
- selector:
- matchLabels:
- app: calendars-backend
- template:
- metadata:
- labels:
- app: calendars-backend
- spec:
- initContainers:
- - name: migrate
- image: calendars-backend
- command: ["python", "manage.py", "migrate", "--no-input"]
- envFrom:
- - configMapRef:
- name: calendars-config
- - configMapRef:
- name: lasuite-postgres
- - configMapRef:
- name: lasuite-oidc-provider
- env:
- - name: DB_PASSWORD
- valueFrom:
- secretKeyRef:
- name: calendars-db-credentials
- key: password
- - name: DJANGO_SECRET_KEY
- valueFrom:
- secretKeyRef:
- name: calendars-django-secret
- key: DJANGO_SECRET_KEY
- - name: SALT_KEY
- valueFrom:
- secretKeyRef:
- name: calendars-django-secret
- key: SALT_KEY
- - name: CALDAV_INBOUND_API_KEY
- valueFrom:
- secretKeyRef:
- name: calendars-django-secret
- key: CALDAV_INBOUND_API_KEY
- - name: CALDAV_OUTBOUND_API_KEY
- valueFrom:
- secretKeyRef:
- name: calendars-django-secret
- key: CALDAV_OUTBOUND_API_KEY
- - name: CALDAV_INTERNAL_API_KEY
- valueFrom:
- secretKeyRef:
- name: calendars-django-secret
- key: CALDAV_INTERNAL_API_KEY
- - name: OIDC_RP_CLIENT_ID
- valueFrom:
- secretKeyRef:
- name: oidc-calendars
- key: CLIENT_ID
- - name: OIDC_RP_CLIENT_SECRET
- valueFrom:
- secretKeyRef:
- name: oidc-calendars
- key: CLIENT_SECRET
- resources:
- limits:
- memory: 512Mi
- cpu: 500m
- requests:
- memory: 128Mi
- cpu: 100m
- containers:
- - name: calendars-backend
- image: calendars-backend
- command:
- - gunicorn
- - -c
- - /app/gunicorn.conf.py
- - calendars.wsgi:application
- ports:
- - containerPort: 8000
- envFrom:
- - configMapRef:
- name: calendars-config
- - configMapRef:
- name: lasuite-postgres
- - configMapRef:
- name: lasuite-oidc-provider
- env:
- - name: DB_PASSWORD
- valueFrom:
- secretKeyRef:
- name: calendars-db-credentials
- key: password
- - name: DJANGO_SECRET_KEY
- valueFrom:
- secretKeyRef:
- name: calendars-django-secret
- key: DJANGO_SECRET_KEY
- - name: SALT_KEY
- valueFrom:
- secretKeyRef:
- name: calendars-django-secret
- key: SALT_KEY
- - name: CALDAV_INBOUND_API_KEY
- valueFrom:
- secretKeyRef:
- name: calendars-django-secret
- key: CALDAV_INBOUND_API_KEY
- - name: CALDAV_OUTBOUND_API_KEY
- valueFrom:
- secretKeyRef:
- name: calendars-django-secret
- key: CALDAV_OUTBOUND_API_KEY
- - name: CALDAV_INTERNAL_API_KEY
- valueFrom:
- secretKeyRef:
- name: calendars-django-secret
- key: CALDAV_INTERNAL_API_KEY
- - name: OIDC_RP_CLIENT_ID
- valueFrom:
- secretKeyRef:
- name: oidc-calendars
- key: CLIENT_ID
- - name: OIDC_RP_CLIENT_SECRET
- valueFrom:
- secretKeyRef:
- name: oidc-calendars
- key: CLIENT_SECRET
- volumeMounts:
- - name: theme
- mountPath: /app/theme.json
- subPath: theme.json
- - name: translations
- mountPath: /data/translations.json
- subPath: translations.json
- livenessProbe:
- tcpSocket:
- port: 8000
- initialDelaySeconds: 15
- periodSeconds: 20
- readinessProbe:
- tcpSocket:
- port: 8000
- initialDelaySeconds: 10
- periodSeconds: 10
- resources:
- limits:
- memory: 512Mi
- cpu: 500m
- requests:
- memory: 256Mi
- cpu: 100m
- volumes:
- - name: theme
- configMap:
- name: calendars-theme
- - name: translations
- configMap:
- name: calendars-translations
diff --git a/base/lasuite/calendars-backend-service.yaml b/base/lasuite/calendars-backend-service.yaml
deleted file mode 100644
index f0c830c..0000000
--- a/base/lasuite/calendars-backend-service.yaml
+++ /dev/null
@@ -1,11 +0,0 @@
-apiVersion: v1
-kind: Service
-metadata:
- name: calendars-backend
- namespace: lasuite
-spec:
- selector:
- app: calendars-backend
- ports:
- - port: 80
- targetPort: 8000
diff --git a/base/lasuite/calendars-caldav-deployment.yaml b/base/lasuite/calendars-caldav-deployment.yaml
deleted file mode 100644
index fc13d44..0000000
--- a/base/lasuite/calendars-caldav-deployment.yaml
+++ /dev/null
@@ -1,97 +0,0 @@
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: calendars-caldav
- namespace: lasuite
-spec:
- replicas: 1
- selector:
- matchLabels:
- app: calendars-caldav
- template:
- metadata:
- labels:
- app: calendars-caldav
- spec:
- initContainers:
- - name: init-database
- image: calendars-caldav
- command: ["/usr/local/bin/init-database.sh"]
- env:
- - name: PGHOST
- valueFrom:
- configMapKeyRef:
- name: lasuite-postgres
- key: DB_HOST
- - name: PGPORT
- valueFrom:
- configMapKeyRef:
- name: lasuite-postgres
- key: DB_PORT
- - name: PGDATABASE
- value: calendars_db
- - name: PGUSER
- value: calendars
- - name: PGPASSWORD
- valueFrom:
- secretKeyRef:
- name: calendars-db-credentials
- key: password
- resources:
- limits:
- memory: 128Mi
- cpu: 100m
- requests:
- memory: 64Mi
- cpu: 10m
- containers:
- - name: calendars-caldav
- image: calendars-caldav
- ports:
- - containerPort: 80
- env:
- - name: PGHOST
- valueFrom:
- configMapKeyRef:
- name: lasuite-postgres
- key: DB_HOST
- - name: PGPORT
- valueFrom:
- configMapKeyRef:
- name: lasuite-postgres
- key: DB_PORT
- - name: PGDATABASE
- value: calendars_db
- - name: PGUSER
- value: calendars
- - name: PGPASSWORD
- valueFrom:
- secretKeyRef:
- name: calendars-db-credentials
- key: password
- - name: CALDAV_INBOUND_API_KEY
- valueFrom:
- secretKeyRef:
- name: calendars-django-secret
- key: CALDAV_INBOUND_API_KEY
- - name: CALDAV_OUTBOUND_API_KEY
- valueFrom:
- secretKeyRef:
- name: calendars-django-secret
- key: CALDAV_OUTBOUND_API_KEY
- - name: CALDAV_INTERNAL_API_KEY
- valueFrom:
- secretKeyRef:
- name: calendars-django-secret
- key: CALDAV_INTERNAL_API_KEY
- - name: CALDAV_BASE_URI
- value: /caldav/
- - name: CALLBACK_BASE_URL
- value: http://calendars-backend.lasuite.svc.cluster.local:8000
- resources:
- limits:
- memory: 256Mi
- cpu: 300m
- requests:
- memory: 128Mi
- cpu: 50m
diff --git a/base/lasuite/calendars-caldav-service.yaml b/base/lasuite/calendars-caldav-service.yaml
deleted file mode 100644
index 6352b2f..0000000
--- a/base/lasuite/calendars-caldav-service.yaml
+++ /dev/null
@@ -1,11 +0,0 @@
-apiVersion: v1
-kind: Service
-metadata:
- name: calendars-caldav
- namespace: lasuite
-spec:
- selector:
- app: calendars-caldav
- ports:
- - port: 80
- targetPort: 80
diff --git a/base/lasuite/calendars-config.yaml b/base/lasuite/calendars-config.yaml
deleted file mode 100644
index af2bd64..0000000
--- a/base/lasuite/calendars-config.yaml
+++ /dev/null
@@ -1,30 +0,0 @@
-apiVersion: v1
-kind: ConfigMap
-metadata:
- name: calendars-config
- namespace: lasuite
-data:
- DJANGO_CONFIGURATION: Production
- DJANGO_SETTINGS_MODULE: calendars.settings
- DJANGO_ALLOWED_HOSTS: cal.DOMAIN_SUFFIX,calendars-backend.lasuite.svc.cluster.local,localhost
- DJANGO_CSRF_TRUSTED_ORIGINS: https://cal.DOMAIN_SUFFIX
- DB_NAME: calendars_db
- DB_USER: calendars
- CALDAV_URL: http://calendars-caldav.lasuite.svc.cluster.local:80
- CALDAV_CALLBACK_BASE_URL: http://calendars-backend.lasuite.svc.cluster.local:8000
- REDIS_URL: redis://valkey.data.svc.cluster.local:6379/5
- DRAMATIQ_BROKER_URL: redis://valkey.data.svc.cluster.local:6379/5
- DRAMATIQ_RESULT_BACKEND_URL: redis://valkey.data.svc.cluster.local:6379/6
- APP_URL: https://cal.DOMAIN_SUFFIX
- DEFAULT_FROM_EMAIL: noreply@sunbeam.pt
- CALENDAR_INVITATION_FROM_EMAIL: calendar@sunbeam.pt
- CALENDAR_ITIP_ENABLED: "True"
- LOGIN_REDIRECT_URL: /
- LOGIN_REDIRECT_URL_FAILURE: /
- LOGOUT_REDIRECT_URL: /
- FRONTEND_THEME: sunbeam
- FRONTEND_HIDE_GAUFRE: "False"
- NEXT_PUBLIC_VISIO_BASE_URL: https://meet.DOMAIN_SUFFIX
- FRONTEND_CSS_URL: https://integration.DOMAIN_SUFFIX/api/v2/theme.css
- OIDC_USERINFO_FULLNAME_FIELDS: given_name,family_name
- THEME_CUSTOMIZATION_FILE_PATH: /app/theme.json
diff --git a/base/lasuite/calendars-frontend-caddyfile.yaml b/base/lasuite/calendars-frontend-caddyfile.yaml
deleted file mode 100644
index 50d11fa..0000000
--- a/base/lasuite/calendars-frontend-caddyfile.yaml
+++ /dev/null
@@ -1,26 +0,0 @@
-apiVersion: v1
-kind: ConfigMap
-metadata:
- name: calendars-frontend-caddyfile
- namespace: lasuite
-data:
- Caddyfile: |
- {
- auto_https off
- admin off
- }
-
- :8080 {
- root * /srv
- header X-Frame-Options DENY
-
- route {
- try_files {path} {path}.html /index.html
- file_server
- }
-
- handle_errors {
- rewrite * /404.html
- file_server
- }
- }
diff --git a/base/lasuite/calendars-frontend-deployment.yaml b/base/lasuite/calendars-frontend-deployment.yaml
deleted file mode 100644
index c720784..0000000
--- a/base/lasuite/calendars-frontend-deployment.yaml
+++ /dev/null
@@ -1,35 +0,0 @@
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: calendars-frontend
- namespace: lasuite
-spec:
- replicas: 1
- selector:
- matchLabels:
- app: calendars-frontend
- template:
- metadata:
- labels:
- app: calendars-frontend
- spec:
- containers:
- - name: calendars-frontend
- image: calendars-frontend
- ports:
- - containerPort: 8080
- volumeMounts:
- - name: caddyfile
- mountPath: /etc/caddy/Caddyfile
- subPath: Caddyfile
- resources:
- limits:
- memory: 128Mi
- cpu: 100m
- requests:
- memory: 64Mi
- cpu: 10m
- volumes:
- - name: caddyfile
- configMap:
- name: calendars-frontend-caddyfile
diff --git a/base/lasuite/calendars-frontend-service.yaml b/base/lasuite/calendars-frontend-service.yaml
deleted file mode 100644
index ad0ddb6..0000000
--- a/base/lasuite/calendars-frontend-service.yaml
+++ /dev/null
@@ -1,11 +0,0 @@
-apiVersion: v1
-kind: Service
-metadata:
- name: calendars-frontend
- namespace: lasuite
-spec:
- selector:
- app: calendars-frontend
- ports:
- - port: 80
- targetPort: 8080
diff --git a/base/lasuite/calendars-theme-configmap.yaml b/base/lasuite/calendars-theme-configmap.yaml
deleted file mode 100644
index f4d68ee..0000000
--- a/base/lasuite/calendars-theme-configmap.yaml
+++ /dev/null
@@ -1,17 +0,0 @@
-apiVersion: v1
-kind: ConfigMap
-metadata:
- name: calendars-theme
- namespace: lasuite
-data:
- theme.json: |
- {
- "css_url": "https://integration.DOMAIN_SUFFIX/api/v2/theme.css",
- "waffle": {
- "apiUrl": "https://integration.DOMAIN_SUFFIX/api/v2/services.json",
- "widgetPath": "https://integration.DOMAIN_SUFFIX/api/v2/lagaufre.js",
- "label": "O Estúdio",
- "closeLabel": "Fechar",
- "newWindowLabelSuffix": " · nova janela"
- }
- }
diff --git a/base/lasuite/calendars-worker-deployment.yaml b/base/lasuite/calendars-worker-deployment.yaml
deleted file mode 100644
index 55792d5..0000000
--- a/base/lasuite/calendars-worker-deployment.yaml
+++ /dev/null
@@ -1,88 +0,0 @@
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: calendars-worker
- namespace: lasuite
-spec:
- replicas: 1
- selector:
- matchLabels:
- app: calendars-worker
- template:
- metadata:
- labels:
- app: calendars-worker
- spec:
- containers:
- - name: calendars-worker
- image: calendars-backend
- command: ["python", "worker.py"]
- envFrom:
- - configMapRef:
- name: calendars-config
- - configMapRef:
- name: lasuite-postgres
- - configMapRef:
- name: lasuite-oidc-provider
- env:
- - name: DB_PASSWORD
- valueFrom:
- secretKeyRef:
- name: calendars-db-credentials
- key: password
- - name: DJANGO_SECRET_KEY
- valueFrom:
- secretKeyRef:
- name: calendars-django-secret
- key: DJANGO_SECRET_KEY
- - name: SALT_KEY
- valueFrom:
- secretKeyRef:
- name: calendars-django-secret
- key: SALT_KEY
- - name: CALDAV_INBOUND_API_KEY
- valueFrom:
- secretKeyRef:
- name: calendars-django-secret
- key: CALDAV_INBOUND_API_KEY
- - name: CALDAV_OUTBOUND_API_KEY
- valueFrom:
- secretKeyRef:
- name: calendars-django-secret
- key: CALDAV_OUTBOUND_API_KEY
- - name: CALDAV_INTERNAL_API_KEY
- valueFrom:
- secretKeyRef:
- name: calendars-django-secret
- key: CALDAV_INTERNAL_API_KEY
- - name: OIDC_RP_CLIENT_ID
- valueFrom:
- secretKeyRef:
- name: oidc-calendars
- key: CLIENT_ID
- - name: OIDC_RP_CLIENT_SECRET
- valueFrom:
- secretKeyRef:
- name: oidc-calendars
- key: CLIENT_SECRET
- volumeMounts:
- - name: theme
- mountPath: /app/theme.json
- subPath: theme.json
- - name: translations
- mountPath: /data/translations.json
- subPath: translations.json
- resources:
- limits:
- memory: 256Mi
- cpu: 300m
- requests:
- memory: 128Mi
- cpu: 50m
- volumes:
- - name: theme
- configMap:
- name: calendars-theme
- - name: translations
- configMap:
- name: calendars-translations
diff --git a/base/lasuite/drive-frontend-nginx-configmap.yaml b/base/lasuite/drive-frontend-nginx-configmap.yaml
deleted file mode 100644
index 3080b74..0000000
--- a/base/lasuite/drive-frontend-nginx-configmap.yaml
+++ /dev/null
@@ -1,88 +0,0 @@
-# nginx config for drive-frontend.
-#
-# /media/ requests are validated via auth_request to the Drive backend before
-# being proxied to SeaweedFS. This avoids exposing S3 credentials to the browser
-# while still serving private files through the CDN path.
-apiVersion: v1
-kind: ConfigMap
-metadata:
- name: drive-frontend-nginx-conf
- namespace: lasuite
-data:
- default.conf: |
- server {
- listen 8080;
- server_name localhost;
- server_tokens off;
-
- root /usr/share/nginx/html;
-
- # Rewrite hardcoded upstream La Gaufre widget and services API URLs to our
- # integration service. sub_filter doesn't work on gzip-compressed responses.
- gzip off;
- sub_filter_once off;
- sub_filter_types text/html application/javascript;
- sub_filter 'https://static.suite.anct.gouv.fr/widgets/lagaufre.js'
- 'https://integration.DOMAIN_SUFFIX/api/v2/lagaufre.js';
- sub_filter 'https://lasuite.numerique.gouv.fr/api/services'
- 'https://integration.DOMAIN_SUFFIX/api/v2/services.json';
- sub_filter 'https://operateurs.suite.anct.gouv.fr/api/v1.0/lagaufre/services/?operator=9f5624fc-ef99-4d10-ae3f-403a81eb16ef&siret=21870030000013'
- 'https://integration.DOMAIN_SUFFIX/api/v2/services.json';
- sub_filter '' '';
-
- # Public file viewer — Next.js static export generates a literal [id].html
- # template for this dynamic route. Serve it for any file UUID so the
- # client-side router hydrates the correct FilePage component without auth.
- location ~ ^/explorer/items/files/[^/]+$ {
- try_files $uri $uri.html /explorer/items/files/[id].html;
- }
-
- # Item detail routes (folders, workspaces, shared items).
- location ~ ^/explorer/items/[^/]+$ {
- try_files $uri $uri.html /explorer/items/[id].html;
- }
-
- location / {
- # Try the exact path, then path + .html (Next.js static export generates
- # e.g. explorer/items/my-files.html), then fall back to index.html for
- # client-side routes that have no pre-rendered file.
- try_files $uri $uri.html /index.html;
- }
-
- # Protected media: auth via Drive backend, then proxy to S3 with signed headers.
- # media-auth returns SigV4 Authorization/X-Amz-Date/X-Amz-Content-SHA256
- # headers signed for the S3 key (item/UUID/file). nginx captures them and
- # forwards to SeaweedFS. The regex strips /media/ and optional /preview/
- # so the proxy path matches the signed S3 key exactly.
- location ~ ^/media/(preview/)?(.*) {
- set $original_uri $request_uri;
- set $s3_key $2;
- resolver kube-dns.kube-system.svc.cluster.local valid=30s;
- set $s3_backend http://seaweedfs-filer.storage.svc.cluster.local:8333;
- auth_request /internal/media-auth;
- auth_request_set $auth_header $upstream_http_authorization;
- auth_request_set $amz_date $upstream_http_x_amz_date;
- auth_request_set $amz_content $upstream_http_x_amz_content_sha256;
- proxy_set_header Authorization $auth_header;
- proxy_set_header X-Amz-Date $amz_date;
- proxy_set_header X-Amz-Content-Sha256 $amz_content;
- proxy_pass $s3_backend/sunbeam-drive/$s3_key;
- }
-
- # Internal subrequest: Django checks session and item access, returns S3 auth headers.
- location = /internal/media-auth {
- internal;
- proxy_pass http://drive-backend.lasuite.svc.cluster.local:80/api/v1.0/items/media-auth/;
- proxy_pass_request_body off;
- proxy_set_header Content-Length "";
- proxy_set_header Cookie $http_cookie;
- proxy_set_header Host drive.DOMAIN_SUFFIX;
- proxy_set_header X-Original-URL https://drive.DOMAIN_SUFFIX$original_uri;
- }
-
- error_page 500 502 503 504 @blank_error;
- location @blank_error {
- return 200 '';
- add_header Content-Type text/html;
- }
- }
diff --git a/base/lasuite/drive-values.yaml b/base/lasuite/drive-values.yaml
deleted file mode 100644
index da7ae44..0000000
--- a/base/lasuite/drive-values.yaml
+++ /dev/null
@@ -1,215 +0,0 @@
-# La Suite Numérique — Drive (drive chart).
-# Env vars use the chart's dict-based envVars schema:
-# string value → rendered as env.value
-# map value → rendered as env.valueFrom (configMapKeyRef / secretKeyRef)
-# DOMAIN_SUFFIX is substituted by sed at deploy time.
-#
-# Required secrets (created by seed script):
-# oidc-drive — CLIENT_ID, CLIENT_SECRET (created by Hydra Maester)
-# drive-db-credentials — password (VaultDynamicSecret, DB engine)
-# drive-django-secret — DJANGO_SECRET_KEY (VaultStaticSecret)
-# seaweedfs-s3-credentials — S3_ACCESS_KEY, S3_SECRET_KEY (shared)
-
-fullnameOverride: drive
-
-backend:
- livenessProbe:
- initialDelaySeconds: 15
- periodSeconds: 10
- timeoutSeconds: 5
- failureThreshold: 3
- readinessProbe:
- initialDelaySeconds: 15
- periodSeconds: 10
- timeoutSeconds: 5
- failureThreshold: 3
- createsuperuser:
- # No superuser — users authenticate via OIDC.
- # The chart always renders this Job; override command so it exits 0.
- command: ["true"]
-
- envVars: &backendEnvVars
- # ── Database ──────────────────────────────────────────────────────────────
- DB_NAME: drive_db
- DB_USER: drive
- DB_HOST:
- configMapKeyRef:
- name: lasuite-postgres
- key: DB_HOST
- DB_PORT:
- configMapKeyRef:
- name: lasuite-postgres
- key: DB_PORT
- # Drive uses psycopg3 backend (no _psycopg2 suffix).
- DB_ENGINE: django.db.backends.postgresql
- DB_PASSWORD:
- secretKeyRef:
- name: drive-db-credentials
- key: password
-
- # ── Redis / Celery ────────────────────────────────────────────────────────
- REDIS_URL:
- configMapKeyRef:
- name: lasuite-valkey
- key: REDIS_URL
- # Drive uses DJANGO_CELERY_BROKER_URL (not CELERY_BROKER_URL).
- DJANGO_CELERY_BROKER_URL:
- configMapKeyRef:
- name: lasuite-valkey
- key: CELERY_BROKER_URL
-
- # ── S3 (file storage) ─────────────────────────────────────────────────────
- AWS_STORAGE_BUCKET_NAME: sunbeam-drive
- AWS_S3_ENDPOINT_URL:
- configMapKeyRef:
- name: lasuite-s3
- key: AWS_S3_ENDPOINT_URL
- AWS_S3_REGION_NAME:
- configMapKeyRef:
- name: lasuite-s3
- key: AWS_S3_REGION_NAME
- AWS_DEFAULT_ACL:
- configMapKeyRef:
- name: lasuite-s3
- key: AWS_DEFAULT_ACL
- # Drive uses AWS_S3_ACCESS_KEY_ID / AWS_S3_SECRET_ACCESS_KEY (with _S3_ prefix).
- AWS_S3_ACCESS_KEY_ID:
- secretKeyRef:
- name: seaweedfs-s3-credentials
- key: S3_ACCESS_KEY
- AWS_S3_SECRET_ACCESS_KEY:
- secretKeyRef:
- name: seaweedfs-s3-credentials
- key: S3_SECRET_KEY
- # Public S3 endpoint for browser-side presigned upload URLs.
- AWS_S3_DOMAIN_REPLACE: https://s3.DOMAIN_SUFFIX
- # Base URL for media file references so nginx auth proxy receives full paths.
- MEDIA_BASE_URL: https://drive.DOMAIN_SUFFIX
-
- # ── OIDC (Hydra) ──────────────────────────────────────────────────────────
- OIDC_RP_CLIENT_ID:
- secretKeyRef:
- name: oidc-drive
- key: CLIENT_ID
- OIDC_RP_CLIENT_SECRET:
- secretKeyRef:
- name: oidc-drive
- key: CLIENT_SECRET
- OIDC_RP_SIGN_ALGO:
- configMapKeyRef:
- name: lasuite-oidc-provider
- key: OIDC_RP_SIGN_ALGO
- OIDC_RP_SCOPES:
- configMapKeyRef:
- name: lasuite-oidc-provider
- key: OIDC_RP_SCOPES
- OIDC_OP_JWKS_ENDPOINT:
- configMapKeyRef:
- name: lasuite-oidc-provider
- key: OIDC_OP_JWKS_ENDPOINT
- OIDC_OP_AUTHORIZATION_ENDPOINT:
- configMapKeyRef:
- name: lasuite-oidc-provider
- key: OIDC_OP_AUTHORIZATION_ENDPOINT
- OIDC_OP_TOKEN_ENDPOINT:
- configMapKeyRef:
- name: lasuite-oidc-provider
- key: OIDC_OP_TOKEN_ENDPOINT
- OIDC_OP_USER_ENDPOINT:
- configMapKeyRef:
- name: lasuite-oidc-provider
- key: OIDC_OP_USER_ENDPOINT
- OIDC_OP_LOGOUT_ENDPOINT:
- configMapKeyRef:
- name: lasuite-oidc-provider
- key: OIDC_OP_LOGOUT_ENDPOINT
- OIDC_VERIFY_SSL:
- configMapKeyRef:
- name: lasuite-oidc-provider
- key: OIDC_VERIFY_SSL
-
- # ── Resource Server (Drive as OAuth2 RS for Messages integration) ─────────
- OIDC_RESOURCE_SERVER_ENABLED: "True"
- # Hydra issuer URL — must match the `iss` claim in introspection responses.
- OIDC_OP_URL: https://auth.DOMAIN_SUFFIX/
- # Hydra token introspection endpoint (admin port — no client auth required).
- OIDC_OP_INTROSPECTION_ENDPOINT: http://hydra-admin.ory.svc.cluster.local:4445/admin/oauth2/introspect
- # Drive authenticates to Hydra introspection using its own OIDC client creds.
- OIDC_RS_CLIENT_ID:
- secretKeyRef:
- name: oidc-drive
- key: CLIENT_ID
- OIDC_RS_CLIENT_SECRET:
- secretKeyRef:
- name: oidc-drive
- key: CLIENT_SECRET
- # Accept bearer tokens from Sunbeam CLI and Messages (server-to-server).
- # OIDC_RS_ALLOWED_AUDIENCES is set by the sunbeam seed script which reads
- # the messages client ID from the oidc-messages secret and combines it with
- # the static sunbeam-cli audience. Stored in vault as secret/drive.
- OIDC_RS_ALLOWED_AUDIENCES:
- secretKeyRef:
- name: drive-rs-audiences
- key: OIDC_RS_ALLOWED_AUDIENCES
-
- # ── Django ────────────────────────────────────────────────────────────────
- DJANGO_SECRET_KEY:
- secretKeyRef:
- name: drive-django-secret
- key: DJANGO_SECRET_KEY
- DJANGO_CONFIGURATION: Production
- ALLOWED_HOSTS: drive.DOMAIN_SUFFIX
- DJANGO_ALLOWED_HOSTS: drive.DOMAIN_SUFFIX
- DJANGO_CSRF_TRUSTED_ORIGINS: https://drive.DOMAIN_SUFFIX
- LOGIN_REDIRECT_URL: /
- LOGOUT_REDIRECT_URL: /
- SESSION_COOKIE_AGE: "604800"
- # Session cache TTL must match SESSION_COOKIE_AGE.
- CACHES_SESSION_TIMEOUT: "604800"
- # Silent login: when the Django session expires, the frontend redirects
- # to the OIDC login endpoint which completes instantly (Hydra already
- # has a session) and bounces the user back. This keeps users logged in
- # seamlessly as long as their Hydra SSO session is valid.
- FRONTEND_SILENT_LOGIN_ENABLED: "true"
- # Redirect unauthenticated visitors at / straight to OIDC login instead of
- # showing the La Suite marketing landing page. returnTo brings them to
- # their files after successful auth.
- FRONTEND_EXTERNAL_HOME_URL: "https://drive.DOMAIN_SUFFIX/api/v1.0/authenticate/?returnTo=https%3A%2F%2Fdrive.DOMAIN_SUFFIX%2Fexplorer%2Fitems%2Fmy-files"
-
- # Allow Messages to call Drive SDK relay cross-origin.
- SDK_CORS_ALLOWED_ORIGINS: "https://mail.DOMAIN_SUFFIX"
- CORS_ALLOWED_ORIGINS: "https://mail.DOMAIN_SUFFIX"
-
- # Allow all file types — self-hosted instance, no need to restrict uploads.
- RESTRICT_UPLOAD_FILE_TYPE: "False"
-
- # ── WOPI / Collabora ──────────────────────────────────────────────────────
- # Comma-separated list of enabled WOPI client names.
- # Inject Sunbeam theme CSS from the integration service.
- FRONTEND_CSS_URL: "https://integration.DOMAIN_SUFFIX/api/v2/theme.css"
-
- WOPI_CLIENTS: collabora
- # Discovery XML endpoint — Collabora registers supported MIME types here.
- WOPI_COLLABORA_DISCOVERY_URL: http://collabora.lasuite.svc.cluster.local:9980/hosting/discovery
- # Base URL Drive uses when building wopi_src callback URLs for Collabora.
- WOPI_SRC_BASE_URL: https://drive.DOMAIN_SUFFIX
-
- themeCustomization:
- enabled: true
- file_content:
- css_url: "https://integration.DOMAIN_SUFFIX/api/v2/theme.css"
- waffle:
- apiUrl: "https://integration.DOMAIN_SUFFIX/api/v2/services.json"
- widgetPath: "https://integration.DOMAIN_SUFFIX/api/v2/lagaufre.js"
- label: "O Estúdio"
- closeLabel: "Fechar"
- newWindowLabelSuffix: " · nova janela"
-
-ingress:
- enabled: false
-
-ingressAdmin:
- enabled: false
-
-ingressMedia:
- enabled: false
diff --git a/base/lasuite/hive-config.yaml b/base/lasuite/hive-config.yaml
deleted file mode 100644
index a260b38..0000000
--- a/base/lasuite/hive-config.yaml
+++ /dev/null
@@ -1,28 +0,0 @@
-apiVersion: v1
-kind: ConfigMap
-metadata:
- name: hive-config
- namespace: lasuite
-data:
- config.toml: |
- [drive]
- base_url = "http://drive-backend.lasuite.svc.cluster.local:80"
- workspace = "Game Assets"
- oidc_client_id = "hive"
- oidc_token_url = "http://hydra.ory.svc.cluster.local:4444/oauth2/token"
- # oidc_client_secret_file = "/run/secrets/hive-oidc" # mounted from Secret
-
- [s3]
- endpoint = "http://seaweedfs-filer.storage.svc.cluster.local:8333"
- bucket = "sunbeam-game-assets"
- region = "us-east-1"
- # access_key_file = "/run/secrets/seaweedfs-key" # mounted from Secret
- # secret_key_file = "/run/secrets/seaweedfs-secret" # mounted from Secret
-
- [postgres]
- # url_file = "/run/secrets/hive-db-url" # mounted from Secret
-
- [sync]
- interval_seconds = 30
- temp_dir = "/tmp/hive"
- large_file_threshold_mb = 50
diff --git a/base/lasuite/hive-deployment.yaml b/base/lasuite/hive-deployment.yaml
deleted file mode 100644
index a3ab976..0000000
--- a/base/lasuite/hive-deployment.yaml
+++ /dev/null
@@ -1,45 +0,0 @@
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: hive
- namespace: lasuite
-spec:
- replicas: 1
- selector:
- matchLabels:
- app: hive
- template:
- metadata:
- labels:
- app: hive
- spec:
- automountServiceAccountToken: false
- containers:
- - name: hive
- image: nginx:alpine # placeholder until La Suite Hive image is built
- volumeMounts:
- - name: config
- mountPath: /etc/hive
- readOnly: true
- - name: secrets
- mountPath: /run/secrets
- readOnly: true
- resources:
- limits:
- memory: 64Mi
- requests:
- memory: 32Mi
- cpu: 25m
- volumes:
- - name: config
- configMap:
- name: hive-config
- - name: secrets
- projected:
- sources:
- - secret:
- name: hive-oidc
- - secret:
- name: seaweedfs-s3-credentials
- - secret:
- name: hive-db-url
diff --git a/base/lasuite/hive-service.yaml b/base/lasuite/hive-service.yaml
deleted file mode 100644
index b54184c..0000000
--- a/base/lasuite/hive-service.yaml
+++ /dev/null
@@ -1,15 +0,0 @@
-# Hive has no inbound HTTP API — it is a reconciliation daemon only.
-# This Service exists for Linkerd observability (metrics scraping).
-apiVersion: v1
-kind: Service
-metadata:
- name: hive
- namespace: lasuite
-spec:
- selector:
- app: hive
- ports:
- - name: metrics
- port: 9090
- targetPort: 9090
- protocol: TCP
diff --git a/base/lasuite/integration-deployment.yaml b/base/lasuite/integration-deployment.yaml
deleted file mode 100644
index 80ed247..0000000
--- a/base/lasuite/integration-deployment.yaml
+++ /dev/null
@@ -1,109 +0,0 @@
-# La Gaufre integration service — O Estúdio app launcher (La Gaufre v2).
-# Serves the lagaufre.js v2 widget, SVG logos, and the v2 services API.
-# Apps load gaufre.js which in turn initialises the v2 widget with the
-# button already rendered by @gouvfr-lasuite/ui-kit.
-#
-# Image: src.DOMAIN_SUFFIX/studio/integration:latest
-# Built from sunbeam/integration-service/ (context: sunbeam/ root)
-# Baked in: lagaufre.js v2, official La Suite logos, custom logos, gaufre.js, nginx.conf
-#
-# ConfigMap: only services.json (v2 format) — the one thing that varies per env
-# DOMAIN_SUFFIX substituted at deploy time.
-
----
-apiVersion: v1
-kind: ConfigMap
-metadata:
- name: integration-config
- namespace: lasuite
-data:
- services.json: |
- {
- "services": [
- {
- "name": "Calendar",
- "url": "https://cal.DOMAIN_SUFFIX",
- "logo": "https://integration.DOMAIN_SUFFIX/logos/calendar.svg?v=1"
- },
- {
- "name": "Drive",
- "url": "https://drive.DOMAIN_SUFFIX",
- "logo": "https://integration.DOMAIN_SUFFIX/logos/drive.svg?v=1"
- },
- {
- "name": "Mail",
- "url": "https://mail.DOMAIN_SUFFIX",
- "logo": "https://integration.DOMAIN_SUFFIX/logos/mail.svg?v=1"
- },
- {
- "name": "Meet",
- "url": "https://meet.DOMAIN_SUFFIX",
- "logo": "https://integration.DOMAIN_SUFFIX/logos/visio.svg?v=2"
- },
- {
- "name": "Projects",
- "url": "https://projects.DOMAIN_SUFFIX",
- "logo": "https://integration.DOMAIN_SUFFIX/logos/projects.svg?v=1"
- },
- {
- "name": "Source Code",
- "url": "https://src.DOMAIN_SUFFIX",
- "logo": "https://integration.DOMAIN_SUFFIX/logos/docs.svg?v=1"
- },
- {
- "name": "Account",
- "url": "https://auth.DOMAIN_SUFFIX",
- "logo": "https://integration.DOMAIN_SUFFIX/logos/account.svg?v=1"
- }
- ]
- }
-
----
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: integration
- namespace: lasuite
-spec:
- replicas: 1
- selector:
- matchLabels:
- app: integration
- template:
- metadata:
- labels:
- app: integration
- spec:
- containers:
- - name: integration
- image: integration
- ports:
- - name: http
- containerPort: 80
- volumeMounts:
- - name: config
- mountPath: /etc/integration/services.json
- subPath: services.json
- resources:
- limits:
- memory: 32Mi
- requests:
- memory: 16Mi
- cpu: 5m
- volumes:
- - name: config
- configMap:
- name: integration-config
----
-apiVersion: v1
-kind: Service
-metadata:
- name: integration
- namespace: lasuite
-spec:
- selector:
- app: integration
- ports:
- - name: http
- port: 80
- targetPort: 80
diff --git a/base/lasuite/kustomization.yaml b/base/lasuite/kustomization.yaml
index 230451a..caa3671 100644
--- a/base/lasuite/kustomization.yaml
+++ b/base/lasuite/kustomization.yaml
@@ -5,15 +5,9 @@ namespace: lasuite
resources:
- namespace.yaml
- - postfix-deployment.yaml
- - hive-config.yaml
- - hive-deployment.yaml
- - hive-service.yaml
- - seaweedfs-buckets.yaml
- shared-config.yaml
- oidc-clients.yaml
- vault-secrets.yaml
- - integration-deployment.yaml
- collabora-deployment.yaml
- collabora-service.yaml
- meet-config.yaml
@@ -23,50 +17,3 @@ resources:
- meet-frontend-nginx-configmap.yaml
- meet-frontend-deployment.yaml
- meet-frontend-service.yaml
- - drive-frontend-nginx-configmap.yaml
- - messages-config.yaml
- - messages-backend-deployment.yaml
- - messages-backend-service.yaml
- - messages-frontend-theme-configmap.yaml
- - messages-frontend-deployment.yaml
- - messages-frontend-service.yaml
- - messages-worker-deployment.yaml
- - messages-mta-in-deployment.yaml
- - messages-mta-in-service.yaml
- - messages-mta-out-deployment.yaml
- - messages-mta-out-service.yaml
- - messages-mpa-dkim-config.yaml
- - messages-mpa-deployment.yaml
- - messages-mpa-service.yaml
- - messages-socks-proxy-deployment.yaml
- - messages-socks-proxy-service.yaml
- - calendars-config.yaml
- - calendars-theme-configmap.yaml
- - calendars-backend-deployment.yaml
- - calendars-backend-service.yaml
- - calendars-caldav-deployment.yaml
- - calendars-caldav-service.yaml
- - calendars-worker-deployment.yaml
- - calendars-frontend-caddyfile.yaml
- - calendars-frontend-deployment.yaml
- - calendars-frontend-service.yaml
- - projects-config.yaml
- - projects-deployment.yaml
-
-patches:
- # Mount media auth proxy nginx config in drive-frontend
- - path: patch-drive-frontend-nginx.yaml
- # Wait for Collabora + run trigger_wopi_configuration on every Drive pod start
- - path: patch-drive-wopi-init.yaml
-
-# La Suite Numérique Helm charts.
-# Charts with a published Helm repo use helmCharts below.
-# find has no published repo yet — deploy manually when OpenSearch is ready.
-helmCharts:
- # helm repo add drive https://suitenumerique.github.io/drive/
- - name: drive
- repo: https://suitenumerique.github.io/drive/
- version: "0.14.0"
- releaseName: drive
- namespace: lasuite
- valuesFile: drive-values.yaml
diff --git a/base/lasuite/messages-backend-deployment.yaml b/base/lasuite/messages-backend-deployment.yaml
deleted file mode 100644
index 6caeddf..0000000
--- a/base/lasuite/messages-backend-deployment.yaml
+++ /dev/null
@@ -1,183 +0,0 @@
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: messages-backend
- namespace: lasuite
-spec:
- replicas: 1
- selector:
- matchLabels:
- app: messages-backend
- template:
- metadata:
- labels:
- app: messages-backend
- spec:
- initContainers:
- - name: migrate
- image: messages-backend
- command: ["python", "manage.py", "migrate", "--no-input"]
- envFrom:
- - configMapRef:
- name: messages-config
- - configMapRef:
- name: lasuite-postgres
- - configMapRef:
- name: lasuite-valkey
- - configMapRef:
- name: lasuite-s3
- - configMapRef:
- name: lasuite-oidc-provider
- env:
- - name: DB_PASSWORD
- valueFrom:
- secretKeyRef:
- name: messages-db-credentials
- key: password
- - name: DJANGO_SECRET_KEY
- valueFrom:
- secretKeyRef:
- name: messages-django-secret
- key: DJANGO_SECRET_KEY
- - name: SALT_KEY
- valueFrom:
- secretKeyRef:
- name: messages-django-secret
- key: SALT_KEY
- - name: MDA_API_SECRET
- valueFrom:
- secretKeyRef:
- name: messages-django-secret
- key: MDA_API_SECRET
- - name: OIDC_RP_CLIENT_ID
- valueFrom:
- secretKeyRef:
- name: oidc-messages
- key: CLIENT_ID
- - name: OIDC_RP_CLIENT_SECRET
- valueFrom:
- secretKeyRef:
- name: oidc-messages
- key: CLIENT_SECRET
- - name: AWS_S3_ACCESS_KEY_ID
- valueFrom:
- secretKeyRef:
- name: seaweedfs-s3-credentials
- key: S3_ACCESS_KEY
- - name: AWS_S3_SECRET_ACCESS_KEY
- valueFrom:
- secretKeyRef:
- name: seaweedfs-s3-credentials
- key: S3_SECRET_KEY
- - name: RSPAMD_PASSWORD
- valueFrom:
- secretKeyRef:
- name: messages-mpa-credentials
- key: RSPAMD_password
- - name: OIDC_STORE_REFRESH_TOKEN_KEY
- valueFrom:
- secretKeyRef:
- name: messages-django-secret
- key: OIDC_STORE_REFRESH_TOKEN_KEY
- - name: OIDC_RP_SCOPES
- value: "openid email profile offline_access"
- resources:
- limits:
- memory: 1Gi
- cpu: 500m
- requests:
- memory: 256Mi
- cpu: 100m
- containers:
- - name: messages-backend
- image: messages-backend
- command:
- - gunicorn
- - -c
- - /app/gunicorn.conf.py
- - messages.wsgi:application
- ports:
- - containerPort: 8000
- envFrom:
- - configMapRef:
- name: messages-config
- - configMapRef:
- name: lasuite-postgres
- - configMapRef:
- name: lasuite-valkey
- - configMapRef:
- name: lasuite-s3
- - configMapRef:
- name: lasuite-oidc-provider
- env:
- - name: DB_PASSWORD
- valueFrom:
- secretKeyRef:
- name: messages-db-credentials
- key: password
- - name: DJANGO_SECRET_KEY
- valueFrom:
- secretKeyRef:
- name: messages-django-secret
- key: DJANGO_SECRET_KEY
- - name: SALT_KEY
- valueFrom:
- secretKeyRef:
- name: messages-django-secret
- key: SALT_KEY
- - name: MDA_API_SECRET
- valueFrom:
- secretKeyRef:
- name: messages-django-secret
- key: MDA_API_SECRET
- - name: OIDC_RP_CLIENT_ID
- valueFrom:
- secretKeyRef:
- name: oidc-messages
- key: CLIENT_ID
- - name: OIDC_RP_CLIENT_SECRET
- valueFrom:
- secretKeyRef:
- name: oidc-messages
- key: CLIENT_SECRET
- - name: AWS_S3_ACCESS_KEY_ID
- valueFrom:
- secretKeyRef:
- name: seaweedfs-s3-credentials
- key: S3_ACCESS_KEY
- - name: AWS_S3_SECRET_ACCESS_KEY
- valueFrom:
- secretKeyRef:
- name: seaweedfs-s3-credentials
- key: S3_SECRET_KEY
- - name: RSPAMD_PASSWORD
- valueFrom:
- secretKeyRef:
- name: messages-mpa-credentials
- key: RSPAMD_password
- - name: OIDC_STORE_REFRESH_TOKEN_KEY
- valueFrom:
- secretKeyRef:
- name: messages-django-secret
- key: OIDC_STORE_REFRESH_TOKEN_KEY
- - name: OIDC_RP_SCOPES
- value: "openid email profile offline_access"
- livenessProbe:
- httpGet:
- path: /__heartbeat__/
- port: 8000
- initialDelaySeconds: 15
- periodSeconds: 20
- readinessProbe:
- httpGet:
- path: /__heartbeat__/
- port: 8000
- initialDelaySeconds: 10
- periodSeconds: 10
- resources:
- limits:
- memory: 1Gi
- cpu: 500m
- requests:
- memory: 256Mi
- cpu: 100m
diff --git a/base/lasuite/messages-backend-service.yaml b/base/lasuite/messages-backend-service.yaml
deleted file mode 100644
index ba5ede4..0000000
--- a/base/lasuite/messages-backend-service.yaml
+++ /dev/null
@@ -1,11 +0,0 @@
-apiVersion: v1
-kind: Service
-metadata:
- name: messages-backend
- namespace: lasuite
-spec:
- selector:
- app: messages-backend
- ports:
- - port: 80
- targetPort: 8000
diff --git a/base/lasuite/messages-config.yaml b/base/lasuite/messages-config.yaml
deleted file mode 100644
index 43fc5ed..0000000
--- a/base/lasuite/messages-config.yaml
+++ /dev/null
@@ -1,45 +0,0 @@
-apiVersion: v1
-kind: ConfigMap
-metadata:
- name: messages-config
- namespace: lasuite
-data:
- DJANGO_CONFIGURATION: Production
- DJANGO_SETTINGS_MODULE: messages.settings
- DJANGO_ALLOWED_HOSTS: mail.DOMAIN_SUFFIX,messages-backend.lasuite.svc.cluster.local
- ALLOWED_HOSTS: mail.DOMAIN_SUFFIX,messages-backend.lasuite.svc.cluster.local
- DJANGO_CSRF_TRUSTED_ORIGINS: https://mail.DOMAIN_SUFFIX
- DB_NAME: messages_db
- DB_USER: messages
- OPENSEARCH_URL: http://opensearch.data.svc.cluster.local:9200
- MDA_API_BASE_URL: http://messages-backend.lasuite.svc.cluster.local:80/api/v1.0/
- MYHOSTNAME: mail.DOMAIN_SUFFIX
- # rspamd URL (auth token injected separately from messages-mpa-credentials secret)
- SPAM_RSPAMD_URL: http://messages-mpa.lasuite.svc.cluster.local:8010/_api
- MESSAGES_FRONTEND_BACKEND_SERVER: messages-backend.lasuite.svc.cluster.local:80
- STORAGE_MESSAGE_IMPORTS_BUCKET_NAME: sunbeam-messages-imports
- STORAGE_MESSAGE_IMPORTS_ENDPOINT_URL: http://seaweedfs-filer.storage.svc.cluster.local:8333
- AWS_STORAGE_BUCKET_NAME: sunbeam-messages
- IDENTITY_PROVIDER: oidc
- FRONTEND_THEME: default
- DRIVE_BASE_URL: https://drive.DOMAIN_SUFFIX
- LOGIN_REDIRECT_URL: https://mail.DOMAIN_SUFFIX
- LOGOUT_REDIRECT_URL: https://mail.DOMAIN_SUFFIX
- OIDC_REDIRECT_ALLOWED_HOSTS: '["https://auth.DOMAIN_SUFFIX"]'
- MTA_OUT_MODE: direct
- # Create user accounts on first OIDC login (required — no pre-provisioning)
- OIDC_CREATE_USER: "True"
- # Redirect to home on auth failure (avoids HttpResponseRedirect(None) → /callback/None 404)
- LOGIN_REDIRECT_URL_FAILURE: https://mail.DOMAIN_SUFFIX
- # Store OIDC tokens in session so the Drive integration can proxy requests on behalf of the user.
- OIDC_STORE_ACCESS_TOKEN: "True"
- OIDC_STORE_REFRESH_TOKEN: "True"
- # Session lives 7 days — long enough to survive overnight/weekend without re-auth.
- # Default is 43200 (12h) which forces a login after a browser restart.
- SESSION_COOKIE_AGE: "604800"
- # Renew the id token 60 s before it expires (access_token TTL = 1h).
- # Without this the default falls back to SESSION_COOKIE_AGE (7 days), which means
- # every request sees the 1h token as "expiring within 7 days" and triggers a
- # prompt=none renewal on every page load — causing repeated auth loops.
- OIDC_RENEW_ID_TOKEN_EXPIRY_SECONDS: "60"
- # offline_access scope is set directly in the deployment env (overrides lasuite-oidc-provider envFrom).
diff --git a/base/lasuite/messages-frontend-deployment.yaml b/base/lasuite/messages-frontend-deployment.yaml
deleted file mode 100644
index a2f09aa..0000000
--- a/base/lasuite/messages-frontend-deployment.yaml
+++ /dev/null
@@ -1,53 +0,0 @@
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: messages-frontend
- namespace: lasuite
-spec:
- replicas: 1
- selector:
- matchLabels:
- app: messages-frontend
- template:
- metadata:
- labels:
- app: messages-frontend
- spec:
- containers:
- - name: messages-frontend
- image: messages-frontend
- ports:
- - containerPort: 8080
- env:
- - name: MESSAGES_FRONTEND_BACKEND_SERVER
- value: messages-backend.lasuite.svc.cluster.local:80
- - name: PORT
- value: "8080"
- livenessProbe:
- httpGet:
- path: /
- port: 8080
- initialDelaySeconds: 10
- periodSeconds: 20
- readinessProbe:
- httpGet:
- path: /
- port: 8080
- initialDelaySeconds: 5
- periodSeconds: 10
- volumeMounts:
- - name: theme
- mountPath: /app/sunbeam-theme.css
- subPath: sunbeam-theme.css
- readOnly: true
- resources:
- limits:
- memory: 256Mi
- cpu: 250m
- requests:
- memory: 64Mi
- cpu: 50m
- volumes:
- - name: theme
- configMap:
- name: messages-frontend-theme
diff --git a/base/lasuite/messages-frontend-service.yaml b/base/lasuite/messages-frontend-service.yaml
deleted file mode 100644
index 3ec68ca..0000000
--- a/base/lasuite/messages-frontend-service.yaml
+++ /dev/null
@@ -1,11 +0,0 @@
-apiVersion: v1
-kind: Service
-metadata:
- name: messages-frontend
- namespace: lasuite
-spec:
- selector:
- app: messages-frontend
- ports:
- - port: 80
- targetPort: 8080
diff --git a/base/lasuite/messages-frontend-theme-configmap.yaml b/base/lasuite/messages-frontend-theme-configmap.yaml
deleted file mode 100644
index 023aee7..0000000
--- a/base/lasuite/messages-frontend-theme-configmap.yaml
+++ /dev/null
@@ -1,50 +0,0 @@
-apiVersion: v1
-kind: ConfigMap
-metadata:
- name: messages-frontend-theme
- namespace: lasuite
-data:
- sunbeam-theme.css: |
- /*
- * O Estúdio — runtime brand overrides for messages-frontend.
- * Loaded via injected in _document.tsx.
- * Override Cunningham v4 --c--globals--* variables (no rebuild for updates).
- */
- @import url('https://fonts.googleapis.com/css2?family=Ysabeau:ital,wght@0,100..900;1,100..900&display=swap');
-
- :root {
- --c--globals--font--families--base: 'Ysabeau Variable', Inter, sans-serif;
- --c--globals--font--families--accent: 'Ysabeau Variable', Inter, sans-serif;
-
- /* Brand — amber/gold palette */
- --c--globals--colors--brand-050: #fffbeb;
- --c--globals--colors--brand-100: #fef3c7;
- --c--globals--colors--brand-150: #fde9a0;
- --c--globals--colors--brand-200: #fde68a;
- --c--globals--colors--brand-250: #fde047;
- --c--globals--colors--brand-300: #fcd34d;
- --c--globals--colors--brand-350: #fbcf3f;
- --c--globals--colors--brand-400: #fbbf24;
- --c--globals--colors--brand-450: #f8b31a;
- --c--globals--colors--brand-500: #f59e0b;
- --c--globals--colors--brand-550: #e8920a;
- --c--globals--colors--brand-600: #d97706;
- --c--globals--colors--brand-650: #c26d05;
- --c--globals--colors--brand-700: #b45309;
- --c--globals--colors--brand-750: #9a4508;
- --c--globals--colors--brand-800: #92400e;
- --c--globals--colors--brand-850: #7c370c;
- --c--globals--colors--brand-900: #78350f;
- --c--globals--colors--brand-950: #451a03;
-
- /* Logo gradient */
- --c--globals--colors--logo-1: #f59e0b;
- --c--globals--colors--logo-2: #d97706;
- --c--globals--colors--logo-1-light: #f59e0b;
- --c--globals--colors--logo-2-light: #d97706;
- --c--globals--colors--logo-1-dark: #fcd34d;
- --c--globals--colors--logo-2-dark: #fbbf24;
-
- /* PWA theme color */
- --sunbeam-brand: #f59e0b;
- }
diff --git a/base/lasuite/messages-mpa-deployment.yaml b/base/lasuite/messages-mpa-deployment.yaml
deleted file mode 100644
index 6341104..0000000
--- a/base/lasuite/messages-mpa-deployment.yaml
+++ /dev/null
@@ -1,56 +0,0 @@
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: messages-mpa
- namespace: lasuite
-spec:
- replicas: 1
- selector:
- matchLabels:
- app: messages-mpa
- template:
- metadata:
- labels:
- app: messages-mpa
- spec:
- containers:
- - name: messages-mpa
- image: messages-mpa
- ports:
- - containerPort: 8010
- env:
- - name: RSPAMD_password
- valueFrom:
- secretKeyRef:
- name: messages-mpa-credentials
- key: RSPAMD_password
- - name: PORT
- value: "8010"
- - name: REDIS_HOST
- value: valkey.data.svc.cluster.local
- - name: REDIS_PORT
- value: "6379"
- volumeMounts:
- - name: dkim-key
- mountPath: /etc/rspamd/dkim
- readOnly: true
- - name: dkim-signing-conf
- mountPath: /etc/rspamd/local.d
- readOnly: true
- resources:
- limits:
- memory: 768Mi
- cpu: 250m
- requests:
- memory: 256Mi
- cpu: 50m
- volumes:
- - name: dkim-key
- secret:
- secretName: messages-dkim-key
- items:
- - key: dkim-private-key
- path: default.sunbeam.pt.key
- - name: dkim-signing-conf
- configMap:
- name: messages-mpa-rspamd-config
diff --git a/base/lasuite/messages-mpa-dkim-config.yaml b/base/lasuite/messages-mpa-dkim-config.yaml
deleted file mode 100644
index baff81e..0000000
--- a/base/lasuite/messages-mpa-dkim-config.yaml
+++ /dev/null
@@ -1,13 +0,0 @@
-apiVersion: v1
-kind: ConfigMap
-metadata:
- name: messages-mpa-rspamd-config
- namespace: lasuite
-data:
- dkim_signing.conf: |
- enabled = true;
- selector = "default";
- path = "/etc/rspamd/dkim/$domain.$selector.key";
- sign_authenticated = true;
- sign_local = true;
- use_domain = "header";
diff --git a/base/lasuite/messages-mpa-service.yaml b/base/lasuite/messages-mpa-service.yaml
deleted file mode 100644
index 73801ae..0000000
--- a/base/lasuite/messages-mpa-service.yaml
+++ /dev/null
@@ -1,11 +0,0 @@
-apiVersion: v1
-kind: Service
-metadata:
- name: messages-mpa
- namespace: lasuite
-spec:
- selector:
- app: messages-mpa
- ports:
- - port: 8010
- targetPort: 8010
diff --git a/base/lasuite/messages-mta-in-deployment.yaml b/base/lasuite/messages-mta-in-deployment.yaml
deleted file mode 100644
index 40832d2..0000000
--- a/base/lasuite/messages-mta-in-deployment.yaml
+++ /dev/null
@@ -1,67 +0,0 @@
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: messages-mta-in
- namespace: lasuite
-spec:
- replicas: 1
- # Recreate: hostPort 25 blocks RollingUpdate — the new pod can't
- # schedule while the old one still holds the port.
- strategy:
- type: Recreate
- selector:
- matchLabels:
- app: messages-mta-in
- template:
- metadata:
- labels:
- app: messages-mta-in
- spec:
- containers:
- - name: messages-mta-in
- image: messages-mta-in
- ports:
- - containerPort: 25
- env:
- - name: MDA_API_BASE_URL
- valueFrom:
- configMapKeyRef:
- name: messages-config
- key: MDA_API_BASE_URL
- - name: MDA_API_SECRET
- valueFrom:
- secretKeyRef:
- name: messages-django-secret
- key: MDA_API_SECRET
- - name: MAX_INCOMING_EMAIL_SIZE
- value: "30000000"
- # Liveness: verify the delivery milter process is running and the
- # unix socket exists. The milter is a long-lived Python process that
- # can hang silently after days of uptime (COE-2026-002 addendum).
- # Without this probe, postfix returns 451 to all inbound mail and
- # nobody notices until senders complain.
- livenessProbe:
- exec:
- command:
- - sh
- - -c
- - "test -S /var/spool/postfix/milter/delivery.sock && kill -0 $(cat /var/run/milter.pid 2>/dev/null || pgrep -f delivery_milter.py)"
- initialDelaySeconds: 15
- periodSeconds: 30
- timeoutSeconds: 5
- failureThreshold: 3
- readinessProbe:
- tcpSocket:
- port: 25
- initialDelaySeconds: 10
- periodSeconds: 15
- securityContext:
- capabilities:
- add: ["NET_BIND_SERVICE"]
- resources:
- limits:
- memory: 256Mi
- cpu: 250m
- requests:
- memory: 64Mi
- cpu: 50m
diff --git a/base/lasuite/messages-mta-in-service.yaml b/base/lasuite/messages-mta-in-service.yaml
deleted file mode 100644
index 0eda54f..0000000
--- a/base/lasuite/messages-mta-in-service.yaml
+++ /dev/null
@@ -1,11 +0,0 @@
-apiVersion: v1
-kind: Service
-metadata:
- name: messages-mta-in
- namespace: lasuite
-spec:
- selector:
- app: messages-mta-in
- ports:
- - port: 25
- targetPort: 25
diff --git a/base/lasuite/messages-mta-out-deployment.yaml b/base/lasuite/messages-mta-out-deployment.yaml
deleted file mode 100644
index d315065..0000000
--- a/base/lasuite/messages-mta-out-deployment.yaml
+++ /dev/null
@@ -1,43 +0,0 @@
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: messages-mta-out
- namespace: lasuite
-spec:
- replicas: 1
- selector:
- matchLabels:
- app: messages-mta-out
- template:
- metadata:
- labels:
- app: messages-mta-out
- spec:
- containers:
- - name: messages-mta-out
- image: messages-mta-out
- ports:
- - containerPort: 587
- env:
- - name: MYHOSTNAME
- valueFrom:
- configMapKeyRef:
- name: messages-config
- key: MYHOSTNAME
- - name: SMTP_USERNAME
- valueFrom:
- secretKeyRef:
- name: messages-mta-out-credentials
- key: SMTP_USERNAME
- - name: SMTP_PASSWORD
- valueFrom:
- secretKeyRef:
- name: messages-mta-out-credentials
- key: SMTP_PASSWORD
- resources:
- limits:
- memory: 256Mi
- cpu: 250m
- requests:
- memory: 64Mi
- cpu: 50m
diff --git a/base/lasuite/messages-mta-out-service.yaml b/base/lasuite/messages-mta-out-service.yaml
deleted file mode 100644
index 0f7c089..0000000
--- a/base/lasuite/messages-mta-out-service.yaml
+++ /dev/null
@@ -1,11 +0,0 @@
-apiVersion: v1
-kind: Service
-metadata:
- name: messages-mta-out
- namespace: lasuite
-spec:
- selector:
- app: messages-mta-out
- ports:
- - port: 587
- targetPort: 587
diff --git a/base/lasuite/messages-socks-proxy-deployment.yaml b/base/lasuite/messages-socks-proxy-deployment.yaml
deleted file mode 100644
index 00775fd..0000000
--- a/base/lasuite/messages-socks-proxy-deployment.yaml
+++ /dev/null
@@ -1,35 +0,0 @@
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: messages-socks-proxy
- namespace: lasuite
-spec:
- replicas: 1
- selector:
- matchLabels:
- app: messages-socks-proxy
- template:
- metadata:
- labels:
- app: messages-socks-proxy
- spec:
- containers:
- - name: messages-socks-proxy
- image: messages-socks-proxy
- ports:
- - containerPort: 1080
- env:
- - name: PROXY_USERS
- valueFrom:
- secretKeyRef:
- name: messages-socks-credentials
- key: PROXY_USERS
- - name: PROXY_SOURCE_IP_WHITELIST
- value: 10.0.0.0/8
- resources:
- limits:
- memory: 128Mi
- cpu: 100m
- requests:
- memory: 32Mi
- cpu: 25m
diff --git a/base/lasuite/messages-socks-proxy-service.yaml b/base/lasuite/messages-socks-proxy-service.yaml
deleted file mode 100644
index 221b561..0000000
--- a/base/lasuite/messages-socks-proxy-service.yaml
+++ /dev/null
@@ -1,11 +0,0 @@
-apiVersion: v1
-kind: Service
-metadata:
- name: messages-socks-proxy
- namespace: lasuite
-spec:
- selector:
- app: messages-socks-proxy
- ports:
- - port: 1080
- targetPort: 1080
diff --git a/base/lasuite/messages-worker-deployment.yaml b/base/lasuite/messages-worker-deployment.yaml
deleted file mode 100644
index 93b79c5..0000000
--- a/base/lasuite/messages-worker-deployment.yaml
+++ /dev/null
@@ -1,90 +0,0 @@
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: messages-worker
- namespace: lasuite
-spec:
- replicas: 1
- selector:
- matchLabels:
- app: messages-worker
- template:
- metadata:
- labels:
- app: messages-worker
- spec:
- containers:
- - name: messages-worker
- image: messages-backend
- command: ["python", "worker.py", "--loglevel=INFO", "--concurrency=3"]
- envFrom:
- - configMapRef:
- name: messages-config
- - configMapRef:
- name: lasuite-postgres
- - configMapRef:
- name: lasuite-valkey
- - configMapRef:
- name: lasuite-s3
- - configMapRef:
- name: lasuite-oidc-provider
- env:
- - name: DB_PASSWORD
- valueFrom:
- secretKeyRef:
- name: messages-db-credentials
- key: password
- - name: DJANGO_SECRET_KEY
- valueFrom:
- secretKeyRef:
- name: messages-django-secret
- key: DJANGO_SECRET_KEY
- - name: SALT_KEY
- valueFrom:
- secretKeyRef:
- name: messages-django-secret
- key: SALT_KEY
- - name: MDA_API_SECRET
- valueFrom:
- secretKeyRef:
- name: messages-django-secret
- key: MDA_API_SECRET
- - name: OIDC_RP_CLIENT_ID
- valueFrom:
- secretKeyRef:
- name: oidc-messages
- key: CLIENT_ID
- - name: OIDC_RP_CLIENT_SECRET
- valueFrom:
- secretKeyRef:
- name: oidc-messages
- key: CLIENT_SECRET
- - name: AWS_S3_ACCESS_KEY_ID
- valueFrom:
- secretKeyRef:
- name: seaweedfs-s3-credentials
- key: S3_ACCESS_KEY
- - name: AWS_S3_SECRET_ACCESS_KEY
- valueFrom:
- secretKeyRef:
- name: seaweedfs-s3-credentials
- key: S3_SECRET_KEY
- - name: RSPAMD_PASSWORD
- valueFrom:
- secretKeyRef:
- name: messages-mpa-credentials
- key: RSPAMD_password
- - name: OIDC_STORE_REFRESH_TOKEN_KEY
- valueFrom:
- secretKeyRef:
- name: messages-django-secret
- key: OIDC_STORE_REFRESH_TOKEN_KEY
- - name: OIDC_RP_SCOPES
- value: "openid email profile offline_access"
- resources:
- limits:
- memory: 1Gi
- cpu: "1"
- requests:
- memory: 256Mi
- cpu: 100m
diff --git a/base/lasuite/patch-drive-frontend-nginx.yaml b/base/lasuite/patch-drive-frontend-nginx.yaml
deleted file mode 100644
index 71cf591..0000000
--- a/base/lasuite/patch-drive-frontend-nginx.yaml
+++ /dev/null
@@ -1,20 +0,0 @@
-# Patch: mount the nginx ConfigMap into drive-frontend to enable the media
-# auth_request proxy (validates Drive session before serving S3 files).
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: drive-frontend
- namespace: lasuite
-spec:
- template:
- spec:
- containers:
- - name: drive
- volumeMounts:
- - name: nginx-conf
- mountPath: /etc/nginx/conf.d/default.conf
- subPath: default.conf
- volumes:
- - name: nginx-conf
- configMap:
- name: drive-frontend-nginx-conf
diff --git a/base/lasuite/patch-drive-wopi-init.yaml b/base/lasuite/patch-drive-wopi-init.yaml
deleted file mode 100644
index b9f9d80..0000000
--- a/base/lasuite/patch-drive-wopi-init.yaml
+++ /dev/null
@@ -1,89 +0,0 @@
-# Init container that waits for Collabora and configures WOPI on every pod start.
-#
-# The Drive chart's configure_wopi Job is designed for ArgoCD PostSync hooks
-# and only runs on `sunbeam apply`. On server restart, no one re-triggers it,
-# so WOPI editing silently breaks. This init container fixes that — every time
-# a Drive backend pod starts (restart, rollout, scale-up), it waits for
-# Collabora and runs trigger_wopi_configuration before the main container.
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: drive-backend
- namespace: lasuite
-spec:
- template:
- spec:
- initContainers:
- - name: configure-wopi
- image: lasuite/drive-backend:latest
- command:
- - "/bin/sh"
- - "-c"
- - |
- echo "Waiting for Collabora..."
- for i in $(seq 1 36); do
- if wget -qO /dev/null --timeout=5 http://collabora.lasuite.svc.cluster.local:9980/hosting/discovery 2>/dev/null; then
- echo "Collabora ready — configuring WOPI..."
- python manage.py trigger_wopi_configuration
- exit $?
- fi
- echo "Attempt $i/36: not ready, retrying in 5s..."
- sleep 5
- done
- echo "WARN: Collabora not ready after 3 minutes — starting without WOPI"
- exit 0
- env:
- # Database — minimum needed for Django manage.py
- - name: DB_ENGINE
- value: django.db.backends.postgresql
- - name: DB_NAME
- value: drive_db
- - name: DB_USER
- value: drive
- - name: DB_HOST
- valueFrom:
- configMapKeyRef:
- name: lasuite-postgres
- key: DB_HOST
- - name: DB_PORT
- valueFrom:
- configMapKeyRef:
- name: lasuite-postgres
- key: DB_PORT
- - name: DB_PASSWORD
- valueFrom:
- secretKeyRef:
- name: drive-db-credentials
- key: password
- # Django
- - name: DJANGO_CONFIGURATION
- value: Production
- - name: DJANGO_SECRET_KEY
- valueFrom:
- secretKeyRef:
- name: drive-django-secret
- key: DJANGO_SECRET_KEY
- # Redis/Celery — trigger_wopi_configuration dispatches a Celery task
- - name: REDIS_URL
- valueFrom:
- configMapKeyRef:
- name: lasuite-valkey
- key: REDIS_URL
- - name: DJANGO_CELERY_BROKER_URL
- valueFrom:
- configMapKeyRef:
- name: lasuite-valkey
- key: CELERY_BROKER_URL
- # WOPI
- - name: WOPI_CLIENTS
- value: collabora
- - name: WOPI_COLLABORA_DISCOVERY_URL
- value: http://collabora.lasuite.svc.cluster.local:9980/hosting/discovery
- - name: WOPI_SRC_BASE_URL
- value: https://drive.DOMAIN_SUFFIX
- resources:
- limits:
- memory: 128Mi
- requests:
- memory: 64Mi
- cpu: 25m
diff --git a/base/lasuite/postfix-deployment.yaml b/base/lasuite/postfix-deployment.yaml
deleted file mode 100644
index 5f194d3..0000000
--- a/base/lasuite/postfix-deployment.yaml
+++ /dev/null
@@ -1,81 +0,0 @@
-# Postfix MTA for the Messages email platform.
-#
-# MTA-out: accepts SMTP from cluster-internal services (Kratos, Messages Django),
-# signs with DKIM, and relays outbound via Scaleway TEM.
-#
-# MTA-in: receives inbound email from the internet (routed via Pingora on port 25).
-# In local dev, no MX record points here so inbound never arrives.
-#
-# Credentials: Secret "postfix-tem-credentials" with keys:
-# smtp_user — Scaleway TEM SMTP username (project ID)
-# smtp_password — Scaleway TEM SMTP password (API key)
-#
-# DKIM keys: Secret "postfix-dkim" with key:
-# private.key — DKIM private key for sunbeam.pt (generated once; add DNS TXT record)
-# selector — DKIM selector (e.g. "mail")
-#
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: postfix
- namespace: lasuite
-spec:
- replicas: 1
- selector:
- matchLabels:
- app: postfix
- template:
- metadata:
- labels:
- app: postfix
- spec:
- automountServiceAccountToken: false
- containers:
- - name: postfix
- image: boky/postfix:latest
- ports:
- - name: smtp
- containerPort: 25
- protocol: TCP
- env:
- # Accept mail from all cluster-internal pods.
- - name: MYNETWORKS
- value: "10.0.0.0/8 172.16.0.0/12 192.168.0.0/16 127.0.0.0/8"
- # Sending domain — replaced by sed at deploy time.
- - name: ALLOWED_SENDER_DOMAINS
- value: "DOMAIN_SUFFIX"
- # Scaleway TEM outbound relay.
- - name: RELAYHOST
- value: "[smtp.tem.scw.cloud]:587"
- - name: SASL_USER
- valueFrom:
- secretKeyRef:
- name: postfix-tem-credentials
- key: smtp_user
- optional: true # allows pod to start before secret exists
- - name: SASL_PASSWORD
- valueFrom:
- secretKeyRef:
- name: postfix-tem-credentials
- key: smtp_password
- optional: true
- resources:
- limits:
- memory: 64Mi
- requests:
- memory: 32Mi
- cpu: 10m
----
-apiVersion: v1
-kind: Service
-metadata:
- name: postfix
- namespace: lasuite
-spec:
- selector:
- app: postfix
- ports:
- - name: smtp
- port: 25
- targetPort: 25
- protocol: TCP
diff --git a/base/lasuite/projects-config.yaml b/base/lasuite/projects-config.yaml
deleted file mode 100644
index 031ebd6..0000000
--- a/base/lasuite/projects-config.yaml
+++ /dev/null
@@ -1,44 +0,0 @@
-apiVersion: v1
-kind: ConfigMap
-metadata:
- name: projects-config
- namespace: lasuite
-data:
- BASE_URL: "https://projects.DOMAIN_SUFFIX"
- TRUST_PROXY: "1"
- NODE_ENV: "production"
-
- # OIDC — Hydra as the identity provider
- OIDC_ISSUER: "https://auth.DOMAIN_SUFFIX/"
- OIDC_SCOPES: "openid email profile"
- OIDC_ENFORCED: "true"
- OIDC_IGNORE_USERNAME: "true"
- OIDC_IGNORE_ROLES: "true"
- OIDC_ADMIN_ROLES: "*"
- OIDC_FULLNAME_ATTRIBUTES: "given_name,family_name"
- # Planka defaults to response_mode=fragment, which returns the auth code in the
- # URL hash (#code=...). The SPA callback handler doesn't parse fragments correctly,
- # causing a silent auth loop. Use query mode so the code comes as ?code=...
- OIDC_RESPONSE_MODE: "query"
-
- # S3 file storage via SeaweedFS
- S3_ENDPOINT: "http://seaweedfs-filer.storage.svc.cluster.local:8333"
- S3_BUCKET: "projects"
- S3_REGION: "us-east-1"
- S3_FORCE_PATH_STYLE: "true"
-
- # SMTP via in-cluster Postfix relay
- SMTP_HOST: "postfix.lasuite.svc.cluster.local"
- SMTP_PORT: "25"
- SMTP_SECURE: "false"
- SMTP_FROM: "Projects "
-
- # La Gaufre waffle menu widget
- REACT_APP_LAGAUFRE_WIDGET_API_URL: "https://integration.DOMAIN_SUFFIX/api/v2/services.json"
- REACT_APP_LAGAUFRE_WIDGET_PATH: "https://integration.DOMAIN_SUFFIX/api/v2/"
-
- # Default language for new OIDC users (browser detection fallback if unset)
- DEFAULT_LANGUAGE: "en-US"
-
- # Permissions
- ALLOW_ALL_TO_CREATE_PROJECTS: "true"
diff --git a/base/lasuite/projects-deployment.yaml b/base/lasuite/projects-deployment.yaml
deleted file mode 100644
index c96f3c9..0000000
--- a/base/lasuite/projects-deployment.yaml
+++ /dev/null
@@ -1,121 +0,0 @@
-# Planka-based Kanban project management — single container (SPA bundled into Sails backend).
-# Image: src.DOMAIN_SUFFIX/studio/projects:latest
-# Built from projects/Dockerfile
-#
-# Secrets injected via env vars:
-# - projects-db-url (VaultDynamicSecret): DATABASE_URL
-# - projects-app-secrets (VaultStaticSecret): SECRET_KEY
-# - oidc-projects (Hydra Maester): CLIENT_ID, CLIENT_SECRET
-# - seaweedfs-s3-credentials (VaultStaticSecret): S3_ACCESS_KEY, S3_SECRET_KEY
----
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: projects
- namespace: lasuite
-spec:
- replicas: 1
- selector:
- matchLabels:
- app: projects
- template:
- metadata:
- labels:
- app: projects
- spec:
- initContainers:
- - name: db-migrate
- image: projects
- command: ["node", "db/init.js"]
- envFrom:
- - configMapRef:
- name: projects-config
- env:
- - name: DATABASE_URL
- valueFrom:
- secretKeyRef:
- name: projects-db-url
- key: url
- - name: SECRET_KEY
- valueFrom:
- secretKeyRef:
- name: projects-app-secrets
- key: SECRET_KEY
- resources:
- limits:
- memory: 256Mi
- requests:
- memory: 128Mi
- cpu: 50m
- containers:
- - name: projects
- image: projects
- command: ["node", "app.js", "--prod"]
- ports:
- - name: http
- containerPort: 1337
- envFrom:
- - configMapRef:
- name: projects-config
- env:
- - name: DATABASE_URL
- valueFrom:
- secretKeyRef:
- name: projects-db-url
- key: url
- - name: SECRET_KEY
- valueFrom:
- secretKeyRef:
- name: projects-app-secrets
- key: SECRET_KEY
- - name: OIDC_CLIENT_ID
- valueFrom:
- secretKeyRef:
- name: oidc-projects
- key: CLIENT_ID
- - name: OIDC_CLIENT_SECRET
- valueFrom:
- secretKeyRef:
- name: oidc-projects
- key: CLIENT_SECRET
- - name: S3_ACCESS_KEY
- valueFrom:
- secretKeyRef:
- name: seaweedfs-s3-credentials
- key: S3_ACCESS_KEY
- - name: S3_SECRET_KEY
- valueFrom:
- secretKeyRef:
- name: seaweedfs-s3-credentials
- key: S3_SECRET_KEY
- resources:
- limits:
- memory: 512Mi
- requests:
- memory: 256Mi
- cpu: 50m
- livenessProbe:
- httpGet:
- path: /
- port: http
- initialDelaySeconds: 15
- periodSeconds: 30
- readinessProbe:
- httpGet:
- path: /
- port: http
- initialDelaySeconds: 10
- periodSeconds: 10
----
-apiVersion: v1
-kind: Service
-metadata:
- name: projects
- namespace: lasuite
-spec:
- selector:
- app: projects
- ports:
- - name: http
- port: 80
- targetPort: 1337
diff --git a/base/lasuite/seaweedfs-buckets.yaml b/base/lasuite/seaweedfs-buckets.yaml
deleted file mode 100644
index 44cca69..0000000
--- a/base/lasuite/seaweedfs-buckets.yaml
+++ /dev/null
@@ -1,45 +0,0 @@
-apiVersion: batch/v1
-kind: Job
-metadata:
- name: seaweedfs-bucket-init
- namespace: lasuite
- annotations:
- # Run once on first deploy; manually delete to re-run if needed.
- helm.sh/hook: post-install
-spec:
- template:
- spec:
- restartPolicy: OnFailure
- containers:
- - name: mc
- image: minio/mc:latest
- command:
- - /bin/sh
- - -c
- - |
- set -e
- ENDPOINT=http://seaweedfs-filer.storage.svc.cluster.local:8333
- mc alias set weed "$ENDPOINT" "$S3_ACCESS_KEY" "$S3_SECRET_KEY"
-
- for bucket in \
- sunbeam-meet \
- sunbeam-drive \
- sunbeam-messages \
- sunbeam-messages-imports \
- sunbeam-conversations \
- sunbeam-git-lfs \
- sunbeam-game-assets \
- sunbeam-ml-models \
- sunbeam-stalwart \
- sunbeam-sccache; do
- mc mb --ignore-existing "weed/$bucket"
- echo "Ensured bucket: $bucket"
- done
-
- # Enable object versioning on buckets that require it.
- # Drive's WOPI GetFile response includes X-WOPI-ItemVersion from S3 VersionId.
- # SeaweedFS doesn't support `mc versioning` — use the S3 API directly.
- mc versioning enable weed/sunbeam-drive || echo "Versioning not supported by SeaweedFS mc, skipping (filer handles versioning natively)"
- envFrom:
- - secretRef:
- name: seaweedfs-s3-credentials
diff --git a/overlays/local/kustomization.yaml b/overlays/local/kustomization.yaml
deleted file mode 100644
index 0283e27..0000000
--- a/overlays/local/kustomization.yaml
+++ /dev/null
@@ -1,85 +0,0 @@
-apiVersion: kustomize.config.k8s.io/v1beta1
-kind: Kustomization
-
-# Local dev overlay — targets Lima VM running k3s on macOS
-# Deploy with: kubectl apply -k overlays/local/
-#
-# NOTE: base/mesh (Linkerd) is excluded here. Linkerd is bootstrapped
-# separately by scripts/local-up.sh via the Linkerd CLI, which avoids
-# the identity cert bootstrapping problem at kustomize render time.
-#
-# DOMAIN_SUFFIX substitution: local-up.sh pipes `kustomize build | sed` to
-# replace DOMAIN_SUFFIX with .sslip.io before kubectl apply.
-
-resources:
- - ../../base/build
- - ../../base/ingress
- - ../../base/ory
- - ../../base/data
- - ../../base/storage
- - ../../base/lasuite
- - ../../base/media
- - ../../base/devtools
- - ../../base/stalwart
- - ../../base/vso
-
-images:
- # La Gaufre v2 integration service — lagaufre.js widget + SVG logos + nginx
- - name: integration
- newName: src.DOMAIN_SUFFIX/studio/integration
- newTag: latest
-
- # amd64-only La Suite images — mirrored to our Gitea registry with a patched
- # OCI index that adds an arm64 alias so Rosetta can run them on the Lima VM.
- # DOMAIN_SUFFIX is substituted by local-up.py at deploy time (sed replacement).
- # Meet — built from source and pushed to Gitea registry.
- - name: meet-backend
- newName: src.DOMAIN_SUFFIX/studio/meet-backend
- newTag: latest
- - name: meet-frontend
- newName: src.DOMAIN_SUFFIX/studio/meet-frontend
- newTag: latest
-
- # Projects (Kanban) — built and pushed by `sunbeam build projects`
- - name: projects
- newName: src.DOMAIN_SUFFIX/studio/projects
- newTag: latest
-
- # Calendars — built from source and pushed to Gitea registry.
- - name: calendars-backend
- newName: src.DOMAIN_SUFFIX/studio/calendars-backend
- newTag: latest
- - name: calendars-caldav
- newName: src.DOMAIN_SUFFIX/studio/calendars-caldav
- newTag: latest
- - name: calendars-frontend
- newName: src.DOMAIN_SUFFIX/studio/calendars-frontend
- newTag: latest
-
-patches:
- # Disable SSL verification for OIDC server-side calls — mkcert CA not trusted in pods
- - path: patch-oidc-verify-ssl.yaml
- target:
- kind: ConfigMap
- name: lasuite-oidc-provider
-
- # Add hostPort for TURN relay range + bind :80/:443 on Lima VM
- - path: values-pingora.yaml
- target:
- kind: Deployment
- name: pingora
-
- # Downgrade LiveKit TURN service from LoadBalancer → ClusterIP (klipper would take hostPort 443)
- - path: values-livekit.yaml
- target:
- kind: Service
- name: livekit-server-turn
-
- # Set SSL_CERT_FILE so Gitea's Go TLS trusts the mkcert wildcard CA for OIDC calls
- - path: patch-gitea-mkcert-ca.yaml
- target:
- kind: Deployment
- name: gitea
-
- # Apply §10.7 memory limits to all Deployments
- - path: values-resources.yaml
diff --git a/overlays/local/patch-gitea-mkcert-ca.yaml b/overlays/local/patch-gitea-mkcert-ca.yaml
deleted file mode 100644
index 12816f2..0000000
--- a/overlays/local/patch-gitea-mkcert-ca.yaml
+++ /dev/null
@@ -1,13 +0,0 @@
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: gitea
- namespace: devtools
-spec:
- template:
- spec:
- containers:
- - name: gitea
- env:
- - name: SSL_CERT_FILE
- value: /run/ca/ca.crt
diff --git a/overlays/local/patch-oidc-verify-ssl.yaml b/overlays/local/patch-oidc-verify-ssl.yaml
deleted file mode 100644
index 3f51c1d..0000000
--- a/overlays/local/patch-oidc-verify-ssl.yaml
+++ /dev/null
@@ -1,7 +0,0 @@
-apiVersion: v1
-kind: ConfigMap
-metadata:
- name: lasuite-oidc-provider
- namespace: lasuite
-data:
- OIDC_VERIFY_SSL: "false"
diff --git a/overlays/local/values-domain.yaml b/overlays/local/values-domain.yaml
deleted file mode 100644
index 77e5880..0000000
--- a/overlays/local/values-domain.yaml
+++ /dev/null
@@ -1,21 +0,0 @@
-# Patch: replace DOMAIN_SUFFIX placeholder with .sslip.io
-# in the Pingora ConfigMap's routing table.
-#
-# How to apply: the local-up.sh script calls:
-# LIMA_IP=$(limactl shell sunbeam hostname -I | awk '{print $1}')
-# sed "s/DOMAIN_SUFFIX/${LIMA_IP}.sslip.io/g" overlays/local/values-domain.yaml | kubectl apply -f -
-#
-# Or use kustomize's replacements feature if the IP is known at kustomize time.
-#
-# This is a strategic merge patch on the pingora-config ConfigMap.
-
-apiVersion: v1
-kind: ConfigMap
-metadata:
- name: pingora-config
- namespace: ingress
-data:
- # DOMAIN_SUFFIX is substituted at deploy time by local-up.sh.
- # The local overlay domain is: .sslip.io
- # Example: 192.168.5.2.sslip.io
- domain-suffix: "LIMA_IP.sslip.io"
diff --git a/overlays/local/values-livekit.yaml b/overlays/local/values-livekit.yaml
deleted file mode 100644
index 4c27efb..0000000
--- a/overlays/local/values-livekit.yaml
+++ /dev/null
@@ -1,10 +0,0 @@
-# Local override: change LiveKit TURN service type from LoadBalancer to ClusterIP.
-# k3s klipper-lb would otherwise bind hostPort 443, conflicting with Pingora.
-# External TURN on port 443 is not needed in local dev (no NAT traversal required).
-apiVersion: v1
-kind: Service
-metadata:
- name: livekit-server-turn
- namespace: media
-spec:
- type: ClusterIP
diff --git a/overlays/local/values-pingora.yaml b/overlays/local/values-pingora.yaml
deleted file mode 100644
index 078dc6a..0000000
--- a/overlays/local/values-pingora.yaml
+++ /dev/null
@@ -1,37 +0,0 @@
-# Patch: local Pingora overrides
-# - ACME disabled (mkcert wildcard cert from pingora-tls Secret)
-# - hostPort for TURN relay range on the Lima VM
-
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: pingora
- namespace: ingress
-spec:
- template:
- spec:
- containers:
- - name: pingora
- imagePullPolicy: IfNotPresent
- ports:
- # Bind HTTP/HTTPS directly to the Lima VM's host network
- - name: http
- containerPort: 80
- hostPort: 80
- protocol: TCP
- - name: https
- containerPort: 443
- hostPort: 443
- protocol: TCP
- # Expose full TURN relay range as hostPort so the Lima VM forwards UDP
- - name: turn-start
- containerPort: 49152
- hostPort: 49152
- protocol: UDP
- - name: turn-end
- containerPort: 49252
- hostPort: 49252
- protocol: UDP
- # acme.enabled = false is the default in pingora-config.yaml.
- # The mkcert cert Secret (pingora-tls) is created by scripts/local-certs.sh
- # before kustomize runs, so it is always present on first apply.
diff --git a/overlays/local/values-resources.yaml b/overlays/local/values-resources.yaml
deleted file mode 100644
index 7bc5ba0..0000000
--- a/overlays/local/values-resources.yaml
+++ /dev/null
@@ -1,188 +0,0 @@
-# Patch: apply §10.7 memory limits to all Deployments in the local overlay.
-# These are intentionally tight to stay within the 12 GB Lima VM budget.
-#
-# Applied as a strategic merge patch. Each stanza targets one Deployment by name.
-
----
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: cloudnative-pg
- namespace: data
-spec:
- template:
- spec:
- containers:
- - name: manager
- resources:
- limits:
- memory: 256Mi
-
----
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: livekit-server
- namespace: media
-spec:
- template:
- spec:
- containers:
- - name: livekit-server
- resources:
- limits:
- memory: 128Mi
-
----
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: pingora
- namespace: ingress
-spec:
- template:
- spec:
- containers:
- - name: pingora
- resources:
- limits:
- memory: 128Mi
-
----
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: valkey
- namespace: data
-spec:
- template:
- spec:
- containers:
- - name: valkey
- resources:
- limits:
- memory: 64Mi
-
----
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: opensearch
- namespace: data
-spec:
- template:
- spec:
- containers:
- - name: opensearch
- env:
- # Reduce JVM heap so it fits within the 512Mi container limit.
- # Base sets -Xms512m -Xmx1g which immediately OOMs the container.
- - name: OPENSEARCH_JAVA_OPTS
- value: "-Xms192m -Xmx256m"
- resources:
- limits:
- memory: 512Mi
- requests:
- memory: 256Mi
-
----
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: seaweedfs-filer
- namespace: storage
-spec:
- template:
- spec:
- containers:
- - name: filer
- resources:
- limits:
- memory: 512Mi
- requests:
- memory: 128Mi
-
----
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: hydra-hydra-maester
- namespace: ory
-spec:
- template:
- spec:
- containers:
- - name: hydra-maester
- resources:
- limits:
- memory: 64Mi
-
----
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: login-ui
- namespace: ory
-spec:
- template:
- spec:
- containers:
- - name: login-ui
- resources:
- limits:
- memory: 192Mi
- requests:
- memory: 64Mi
-
----
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: hive
- namespace: lasuite
-spec:
- template:
- spec:
- containers:
- - name: hive
- resources:
- limits:
- memory: 64Mi
-
----
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: collabora
- namespace: lasuite
-spec:
- template:
- spec:
- containers:
- - name: collabora
- resources:
- limits:
- memory: 512Mi
- cpu: 500m
- requests:
- memory: 256Mi
- cpu: 50m
-
----
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: buildkitd
- namespace: build
-spec:
- template:
- spec:
- containers:
- - name: buildkitd
- resources:
- requests:
- cpu: "250m"
- memory: "256Mi"
- limits:
- cpu: "2"
- memory: "2Gi"
diff --git a/overlays/production/kustomization.yaml b/overlays/production/kustomization.yaml
index b8d7193..79e5a71 100644
--- a/overlays/production/kustomization.yaml
+++ b/overlays/production/kustomization.yaml
@@ -27,11 +27,6 @@ resources:
- postgres-scheduled-backup.yaml
images:
- # La Gaufre integration service — built and pushed by `sunbeam build integration`
- - name: integration
- newName: src.DOMAIN_SUFFIX/studio/integration
- newTag: latest
-
# Meet — built from source and pushed to Gitea registry.
- name: meet-backend
newName: src.DOMAIN_SUFFIX/studio/meet-backend
@@ -40,42 +35,6 @@ images:
newName: src.DOMAIN_SUFFIX/studio/meet-frontend
newTag: latest
- # Messages — built from source and pushed to Gitea registry.
- - name: messages-backend
- newName: src.DOMAIN_SUFFIX/studio/messages-backend
- newTag: latest
- - name: messages-frontend
- newName: src.DOMAIN_SUFFIX/studio/messages-frontend
- newTag: latest
- - name: messages-mta-in
- newName: src.DOMAIN_SUFFIX/studio/messages-mta-in
- newTag: latest
- - name: messages-mta-out
- newName: src.DOMAIN_SUFFIX/studio/messages-mta-out
- newTag: latest
- - name: messages-mpa
- newName: src.DOMAIN_SUFFIX/studio/messages-mpa
- newTag: latest
- - name: messages-socks-proxy
- newName: src.DOMAIN_SUFFIX/studio/messages-socks-proxy
- newTag: latest
-
- # Calendars — built from source and pushed to Gitea registry.
- - name: calendars-backend
- newName: src.DOMAIN_SUFFIX/studio/calendars-backend
- newTag: latest
- - name: calendars-caldav
- newName: src.DOMAIN_SUFFIX/studio/calendars-caldav
- newTag: latest
- - name: calendars-frontend
- newName: src.DOMAIN_SUFFIX/studio/calendars-frontend
- newTag: latest
-
- # Projects (Kanban) — built and pushed by `sunbeam build projects`
- - name: projects
- newName: src.DOMAIN_SUFFIX/studio/projects
- newTag: latest
-
# Tuwunel Matrix homeserver — built and pushed by `sunbeam build tuwunel`
- name: tuwunel
newName: src.DOMAIN_SUFFIX/studio/tuwunel
diff --git a/overlays/production/patch-mta-in-hostport.yaml b/overlays/production/patch-mta-in-hostport.yaml
deleted file mode 100644
index 69e3292..0000000
--- a/overlays/production/patch-mta-in-hostport.yaml
+++ /dev/null
@@ -1,15 +0,0 @@
-# Bind MTA-in port 25 to the host so inbound email reaches the pod directly.
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: messages-mta-in
- namespace: lasuite
-spec:
- template:
- spec:
- containers:
- - name: messages-mta-in
- ports:
- - containerPort: 25
- hostPort: 25
- protocol: TCP
diff --git a/overlays/production/values-resources.yaml b/overlays/production/values-resources.yaml
index b22b7a8..25ec111 100644
--- a/overlays/production/values-resources.yaml
+++ b/overlays/production/values-resources.yaml
@@ -149,23 +149,6 @@ spec:
limits:
memory: 128Mi
----
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: hive
- namespace: lasuite
-spec:
- template:
- spec:
- containers:
- - name: hive
- resources:
- requests:
- memory: 64Mi
- limits:
- memory: 256Mi
-
---
apiVersion: apps/v1
kind: Deployment