first prototype

This commit is contained in:
2026-09-27 09:52:00 +02:00
parent 4635199a41
commit 6d011d474f
109 changed files with 6354 additions and 507 deletions
+64
View File
@@ -0,0 +1,64 @@
# Wizard online
An online version of the card game Wizard (rules: `wizard_instructions/`).
| Component | Path | Tech |
|-----------|------|------|
| Frontend | `wizard_website/` | React + TypeScript + Vite, CSS modules, served by nginx |
| Game server | `wizard_server/` | Python, FastAPI, websockets |
| Game logic | `wizard_server/game_logic/` | Pure Python package `wizard_game` (no dependencies) |
| 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)
```
## How it works
1. A player opens the website, enters a name and creates a lobby (and joins it).
2. The lobby shows a code (and an invite link, `?lobby=CODE`) others use to join.
3. The host can add AI players, toggle the *not equal* / *hidden bids* rules, and start the game (3–6 players).
4. The server runs the game with `wizard_game` and sends every player a personal view
(`Observation`) after each move. Reloading the page reconnects to the same seat.
A player who leaves a running game is replaced by an AI player.
5. When an AI seat has to act, the server sends its `Observation` to the AI service over the
internal websocket and applies the answered action. If the AI service is unavailable or
too slow, a random legal move is played so games never get stuck.
The `Observation` / action JSON format is defined once in `wizard_game` and shared by the
frontend, the server and the AI, so AI models see exactly the same data in training and in
production.
## Deployment
```bash
cp .env.example .env # set AI_SHARED_SECRET
docker network create wizard_website # if they don't exist yet
docker network create wizard_api
docker compose up -d --build
```
- `wizard_website` joins the external network `wizard_website` (port 8082).
- `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`.
Trained AI checkpoints go into `wizard_ai/models/latest/` (mounted read-only). Until one exists
the AI service uses the built-in heuristic player.
## Development
```bash
python -m venv .venv && . .venv/bin/activate
pip install -r wizard_server/requirements-dev.txt -r wizard_ai/requirements-dev.txt
(cd wizard_server && uvicorn app.main:app --reload) # :8000
(cd wizard_ai && python -m wizard_ai serve) # connects to :8000
(cd wizard_website && npm install && npm run dev) # :5173
(cd wizard_server && pytest) # game logic + server tests
(cd wizard_ai && pytest)
```