Serve API and website behind Caddy path prefixes
Caddy forwards /wizard/api/* and /wizard/website/* with the prefix stripped, so the server received /ws instead of /api/ws and the website connected to /api/ws on the domain root. - Server routes are now /ws and /health (was /api/ws, /api/health) - Website derives the websocket URL from its own location (../api/ws), giving /wizard/api/ws in production and /api/ws in development - Vite dev proxy strips /api like the production proxy - nginx back to the plain SPA config since Caddy strips the prefix - /internal/ai rejects requests that came through the reverse proxy, in addition to the shared secret - Docs updated for the prefixed deployment Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
@@ -10,8 +10,8 @@ An online version of the card game Wizard (rules: `wizard_instructions/`).
|
||||
| AI player | `wizard_ai/` | Python; RL training skeleton + websocket service |
|
||||
|
||||
```
|
||||
browser ──wss /api/ws──▶ Caddy ──▶ wizard_server ◀──ws /internal/ai── wizard_ai
|
||||
──https /──────▶ Caddy ──▶ wizard_website (network wizard_internal)
|
||||
browser ──wss /wizard/api/ws──────▶ Caddy ──/ws──▶ wizard_server:8083 ◀──ws /internal/ai── wizard_ai
|
||||
──https /wizard/website/──▶ Caddy ──/────▶ wizard_website:8082 (network wizard_internal)
|
||||
```
|
||||
|
||||
## How it works
|
||||
@@ -43,8 +43,11 @@ docker compose up -d --build
|
||||
- `wizard_server` joins the external network `wizard_api` (port 8083) and `wizard_internal`.
|
||||
- `wizard_ai` joins only `wizard_internal`, created by compose as an internal network.
|
||||
|
||||
Add a site block like `Caddyfile.example` to the existing Caddy container: `/api/*` goes to
|
||||
`wizard_server:8083`, everything else to `wizard_website:8082`.
|
||||
In the Caddy reverse proxy, `/wizard/website/*` goes to `wizard_website:8082`
|
||||
and `/wizard/api/*` to `wizard_server:8083`, both with the prefix stripped. The website uses
|
||||
relative asset paths and derives the API address from its own URL (`../api/ws`), so it works under
|
||||
any prefix as long as the website and API are siblings. `/internal/ai` refuses requests that come
|
||||
through the proxy (forwarding headers present), in addition to requiring `AI_SHARED_SECRET`.
|
||||
|
||||
Trained AI checkpoints go into `wizard_ai/models/latest/` (mounted read-only). Until one exists
|
||||
the AI service uses the built-in heuristic player.
|
||||
|
||||
Reference in New Issue
Block a user