feat(deploy): public hosting at cannamanage.plate-software.de + fix systemic auth-token bug
CI — Build, Lint & Security Scan / backend (push) Failing after 1m4s
CI — Build, Lint & Security Scan / frontend (push) Failing after 1m24s
CI — Build, Lint & Security Scan / image-scan (push) Has been skipped
CI — Build, Lint & Security Scan / secrets-scan (push) Failing after 21s
Deploy to TrueNAS / deploy (push) Failing after 4m0s
CI — Build, Lint & Security Scan / backend (push) Failing after 1m4s
CI — Build, Lint & Security Scan / frontend (push) Failing after 1m24s
CI — Build, Lint & Security Scan / image-scan (push) Has been skipped
CI — Build, Lint & Security Scan / secrets-scan (push) Failing after 21s
Deploy to TrueNAS / deploy (push) Failing after 4m0s
Auth fix (the real unblocker): - Add server-side proxy Route Handler app/api/backend/[...path]/route.ts that reads the NextAuth session via auth() and injects Authorization: Bearer on every API call. Method-agnostic; streams raw request body (multipart uploads) and upstream response body (binary PDF/CSV downloads). Replaces the static next.config.mjs rewrite, which could not inject a header — the root cause of every authenticated browser fetch hitting the backend unauthenticated. - Expose session.accessToken in the auth.ts session() callback (+ type aug). Uses auth() not getToken() so cookie handling is correct across the public HTTPS (Apache) -> internal HTTP (container) proxy boundary. - No service files changed; all 24 services already call /api/backend/*. Verified live: NextAuth login -> GET /api/backend/members -> HTTP 200. Public hosting (same proven chain as Gitea/InspectFlow): - docker-compose.truenas.yml: NEXTAUTH_URL/AUTH_URL -> https public origin, rotate AUTH_SECRET + JWT_SECRET + DB_PASSWORD off the committed dev defaults. - deploy.yml: inject AUTH_SECRET/JWT_SECRET/DB_PASSWORD from Gitea secrets; reconcile the live Postgres role password (volume keeps old pw on re-deploy). - frpc on TrueNAS tunnels frontend :3000 -> VPS frps :30010; IONOS Apache terminates TLS for cannamanage.plate-software.de and proxies through frp.
This commit is contained in:
@@ -1,20 +1,48 @@
|
||||
# TrueNAS homelab override — replaces localhost with 192.168.188.119
|
||||
# TrueNAS homelab override — public hosting at https://cannamanage.plate-software.de
|
||||
# Applied on top of docker-compose.yml for the homelab deployment on TrueNAS.local.
|
||||
# Usage:
|
||||
# docker compose -f docker-compose.yml -f docker-compose.truenas.yml up -d --build
|
||||
#
|
||||
# Topology (same proven chain as Gitea + InspectFlow):
|
||||
# browser ──HTTPS──> IONOS Apache (82.165.206.45, TLS via acme.sh)
|
||||
# ──ProxyPass──> VPS frps (85.214.154.199:30010)
|
||||
# ──frp tunnel──> TrueNAS frpc ──> frontend:3000 (this stack)
|
||||
# frontend proxies /api/backend/* to backend:8080 via the server-side
|
||||
# Route Handler (src/app/api/backend/[...path]/route.ts), so only the
|
||||
# frontend port needs to be tunnelled — no separate API exposure.
|
||||
#
|
||||
# Usage (run by the Gitea act_runner on push to main):
|
||||
# docker compose -f docker-compose.yml -f docker-compose.truenas.yml \
|
||||
# -p cannamanage up -d --build --remove-orphans
|
||||
services:
|
||||
db:
|
||||
# POSTGRES_PASSWORD only takes effect on FIRST volume init; the existing
|
||||
# cannamanage_pgdata volume keeps its current role password. The live role
|
||||
# password is rotated out-of-band via `ALTER USER` to match ${DB_PASSWORD}.
|
||||
# This value is here so a fresh volume initialises with the prod password.
|
||||
environment:
|
||||
POSTGRES_PASSWORD: ${DB_PASSWORD:-cannamanage_dev}
|
||||
|
||||
backend:
|
||||
# Host port 8080 is taken by odysseus-searxng-1; remap to 8081.
|
||||
# !override replaces the inherited ports list (compose merges lists by concat otherwise).
|
||||
# Internal container port stays 8080 so frontend's BACKEND_URL=http://backend:8080 is unaffected.
|
||||
ports: !override
|
||||
- "8081:8080"
|
||||
environment:
|
||||
# Real production password (must match the live DB role, see ALTER USER above).
|
||||
SPRING_DATASOURCE_PASSWORD: ${DB_PASSWORD:-cannamanage_dev}
|
||||
# Rotated production JWT signing key (base64 — JwtService base64-decodes it).
|
||||
# Rotating this invalidates all previously issued access/refresh tokens.
|
||||
CANNAMANAGE_SECURITY_JWT_SECRET: ${JWT_SECRET}
|
||||
|
||||
frontend:
|
||||
environment:
|
||||
NEXTAUTH_URL: http://192.168.188.119:3000
|
||||
AUTH_URL: http://192.168.188.119:3000
|
||||
# NextAuth v5 (Auth.js) reads AUTH_SECRET, not NEXTAUTH_SECRET. Without it at
|
||||
# runtime, signIn throws MissingSecret -> the app error boundary shows 'Oops'.
|
||||
# Public origin so NextAuth callbacks/cookies resolve to the HTTPS host.
|
||||
NEXTAUTH_URL: https://cannamanage.plate-software.de
|
||||
AUTH_URL: https://cannamanage.plate-software.de
|
||||
# NextAuth v5 (Auth.js) reads AUTH_SECRET. Rotating it invalidates sessions.
|
||||
AUTH_SECRET: ${AUTH_SECRET}
|
||||
# Trust the X-Forwarded-* headers from the Apache/frp chain (we terminate
|
||||
# TLS upstream and proxy plain HTTP into the container).
|
||||
AUTH_TRUST_HOST: "true"
|
||||
# Server-side proxy target for /api/backend/* (internal compose DNS).
|
||||
BACKEND_URL: http://backend:8080
|
||||
|
||||
Reference in New Issue
Block a user