- Replace in-memory auth sessions with signed cookies and signed OAuth state
- Add auth route coverage and update panel/web server wiring
- Switch test script to per-file Bun processes and clean up type checks
Add chess as the first game plugin using the existing multiplayer framework.
Server-side game logic uses chess.js with server-authoritative clock management.
Client uses react-chessboard v5 with cburnett piece set, drag-and-drop + click-to-move,
configurable time controls (bullet/blitz/rapid/classical/none), draw offers,
resignation, and timeout detection. Extends the game framework with room creation
options to support per-game configuration. Includes 57 tests covering all code paths.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Consolidate room leave/delete event handling into RoomManager emitter,
remove redundant PLAYER_LEFT publishes from GameServer, and delete the
chess game plugin (board, types, tests) in favor of the new plugin
architecture. Add per-module CLAUDE.md files for leveling, guild-settings,
feature-flags, db, api, and panel to improve agent navigability.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Backend:
- Fix session never being attached to ws.data at upgrade time
- Add GameServer class: connection registry, per-connection room tracking,
automatic room cleanup on disconnect via ws.data.rooms
- Replace ws-handler.ts with typed event-driven architecture using mitt
- Remove redundant subscription tracking from RoomManager
- Add JOIN_RESULT with player/spectator lists replacing error-as-control-flow
- Add SESSION_REPLACED for multi-tab same-account detection
- Add FILL_ROOM command for admin solo testing (fills empty slots with host)
- Fix dual-schema routing; remove game types from WsMessageSchema
- Per-player personalized views sent directly after each action
Chess plugin:
- Allow same-player (solo) mode: skip color/turn ownership checks
- Fix forfeit and disconnect handling in solo mode (winner: null)
Frontend:
- Click-to-move with legal move dots and last-move highlight
- Auto-scroll move history, forfeit confirmation, turn-reactive board border
- JOIN_RESULT initialises player/spectator lists immediately on join
- Contextual connecting state, player slot cards in waiting room
- Copy-invite button with Copied! flash, Back to Lobby CTA on finish
- Session-replaced warning banner with Rejoin here action
- Lobby passes preferAs intent through route state
- Admin waiting room shows Start Solo Test button
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Swap the custom move validation and Unicode piece grid for chess.js
(full rules engine with check/checkmate/castling/en passant/promotion)
and react-chessboard (drag-and-drop SVG board). Board styled to match
the purple dark theme and auto-orients to the player's color.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Adds a React admin panel (panel/) with Discord OAuth2 login,
live dashboard via WebSocket, and settings/management pages.
Includes Docker build support, Vite proxy config for dev,
game_settings migration, and open-redirect protection on auth callback.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- Remove 31 unused packages: React, Tailwind, Radix UI, etc.
- Clean up web/tsconfig.json (remove JSX, DOM lib)
- Remove old web/dist/ build artifacts
Web dashboard is now API-only, no UI dependencies needed
Move all web dashboard dependencies from web/package.json into root:
- React 19 + React Router 7
- Radix UI components (14 packages)
- Tailwind CSS v4 + bun-plugin-tailwind
- Recharts, React Hook Form, Zod validation
- Dev dependencies: @types/react, @types/react-dom, tailwindcss
This fixes a production issue where web dependencies weren't being
installed in Dockerfile.prod, even though bot/index.ts imports from
web/src/server at runtime.
VPS deployments using Dockerfile.prod will now have all required
dependencies in a single node_modules.