feat: WM2026 Tippspiel - Initial Backend + Frontend

This commit is contained in:
Ronny Mueller
2026-04-03 22:02:05 +02:00
parent 1c685b90a0
commit e967f36f6c
7 changed files with 4453 additions and 0 deletions
+403
View File
@@ -0,0 +1,403 @@
# Projektplan: WM 2026 Tippspiel — Staffbase Custom Plugin
**Projekt:** WM 2026 Tippspiel
**Auftraggeber:** GEALAN Fenster-Systeme GmbH
**Erstellt:** April 2026
**Version:** 1.0
**Status:** Initialisierung
---
## 1. Projektziel & Vision
### 1.1 Zielsetzung
Entwicklung eines interaktiven Tippspiel-Plugins für die FIFA Weltmeisterschaft 2026 (USA/Kanada/Mexiko, 11. Juni 19. Juli 2026), das nahtlos in die bestehende Staffbase-Mitarbeiter-App von GEALAN integriert wird. Alle Mitarbeitenden können über die gewohnte Staffbase-Oberfläche — auf Mobile und Desktop — ihre Tipps abgeben, Ergebnisse verfolgen und die Rangliste einsehen.
### 1.2 Kernziele
- Mitarbeiterbindung und -engagement rund um die WM 2026 stärken
- Niedrigschwellige Teilnahme: kein separates Login, keine externe App nötig
- Vollständige Integration in die bestehende Staffbase-Instanz von GEALAN
- Mehrsprachige Unterstützung (Deutsch, Englisch — erweiterbar)
- Skalierbar für zukünftige Turniere (EM, CL etc.)
### 1.3 Nicht-Ziele (Out of Scope v1.0)
- Echte Geldwetten oder externe Zahlungsabwicklung
- Integration mit externen sozialen Netzwerken
- Eigene mobile App (kein separates iOS/Android-App-Release)
---
## 2. Technische Architektur
### 2.1 Integrationsmodell: Staffbase Custom Plugin
Das Tippspiel wird als **Staffbase Custom Plugin** realisiert. Custom Plugins sind externe Web-Applikationen, die per **iFrame** in die Staffbase-Plattform eingebettet werden. Staffbase übernimmt die Authentifizierung der Mitarbeitenden automatisch über **JWT-Tokens (RS256)**, sodass kein separates Benutzerkonto für das Tippspiel benötigt wird.
**Vorteile dieses Ansatzes:**
- Vollständige technische Freiheit bei Backend, Frontend und Datenbank
- Automatisches Single Sign-On via Staffbase JWT
- Funktioniert auf iOS-App, Android-App und Web-Browser
- Keine Änderungen an der Staffbase-Instanz selbst notwendig
### 2.2 Architektur-Übersicht
```
┌─────────────────────────────────────────────┐
│ Staffbase-Plattform (GEALAN) │
│ │
│ ┌──────────────────────────────────────┐ │
│ │ Custom Plugin (iFrame) │ │
│ │ → Tippspiel-Frontend (React) │ │
│ └──────────────┬───────────────────────┘ │
│ │ JWT Token (automatisch) │
└─────────────────│───────────────────────────┘
│ HTTPS
┌────────▼─────────┐
│ Backend API │
│ (Node.js/Express)│
│ + JWT-Validierung│
└────────┬──────────┘
┌────────▼──────────┐
│ Datenbank │
│ (PostgreSQL) │
│ Supabase Managed │
└───────────────────┘
┌────────▼──────────┐
│ WM-Spielplan API │
│ football-data.org│
└───────────────────┘
```
### 2.3 Technologie-Stack
| Schicht | Technologie | Begründung |
|---|---|---|
| **Frontend** | React + TypeScript | Moderner Standard, große Community, passt zu Staffbase Client SDK |
| **Staffbase Integration** | @staffbase/plugins-client-sdk | Offizielle Brücke zwischen iFrame und Staffbase-App |
| **Backend** | Node.js + Express | Passt nahtlos zum Staffbase Node.js SDK |
| **Auth / SSO** | @staffbase/staffbase-plugin-sdk | JWT-Validierung (RS256/PKCS8) |
| **Datenbank** | PostgreSQL via Supabase | Managed, DSGVO-konform (EU-Region wählbar), einfaches Setup |
| **Hosting** | Railway oder Render | HTTPS out-of-the-box, einfaches Deployment, kostengünstig |
| **WM-Spielplan** | football-data.org API | Kostenfreie WM-Daten inkl. Ergebnisse, Teams, Gruppen |
| **Caching** | Redis (optional) | Spielplandaten cachen, Rate-Limit-Entlastung |
| **CI/CD** | GitHub Actions | Automatisiertes Deployment |
### 2.4 Staffbase SDK — Verfügbare Nutzerdaten via JWT
Bei jedem Aufruf des Plugins stellt Staffbase automatisch folgende Nutzerdaten bereit:
| Feld | Beschreibung | Verwendung im Tippspiel |
|---|---|---|
| `userId` | Eindeutige Staffbase-User-ID | Primärschlüssel für Tipps & Rangliste |
| `fullName` | Vollständiger Name | Anzeigename in der Rangliste |
| `locale` | Spracheinstellung (z.B. `de_DE`) | Automatische Sprachumschaltung |
| `role` | Staffbase-Rolle (admin, reader…) | Admin-Bereich nur für Admins sichtbar |
| `branchId` | Instanz-/Bereichs-ID | Für standortbezogene Auswertungen |
---
## 3. Funktionsumfang (Features)
### 3.1 Kernfunktionen (MVP — Pflicht für v1.0)
#### F1 — Benutzer & Authentifizierung
- Automatischer Login via Staffbase SSO (JWT) — kein separates Konto
- Benutzerprofil mit Name und Gesamtpunkten
- Rollenbasierter Zugriff: Normaler Nutzer vs. Admin
#### F2 — WM-Spielplan
- Anzeige aller 104 WM-Spiele (Gruppenphase + KO-Runde)
- Automatische Synchronisation mit football-data.org API
- Anzeige von Datum, Uhrzeit (lokalisiert), Stadion, Teams, aktueller Ergebnisstatus
#### F3 — Tipp-Eingabe
- Tipp abgeben: Ergebnis (Heimtore : Auswärtstore) pro Spiel
- Tipp nur möglich bis Anpfiff (Deadline-Schutz)
- Tipp-Änderung bis zur Deadline erlaubt
- Visuelle Bestätigung bei gespeichertem Tipp
#### F4 — Punkte-System
- **Ergebnis exakt richtig:** 3 Punkte
- **Tendenz richtig (Sieg/Remis/Niederlage):** 1 Punkt
- **Falsch:** 0 Punkte
- Bonus-Punkte für KO-Runde konfigurierbar (z.B. ×2 ab Halbfinale)
- Automatische Berechnung nach Ergebnis-Eintrag durch Admin
#### F5 — Rangliste
- Live-Gesamtrangliste aller Teilnehmenden
- Anzeige: Platz, Name, Punkte, Tipp-Quote
- Filterbar nach Abteilung oder Standort (via Staffbase-Gruppen)
- Eigene Position stets sichtbar (auch wenn außerhalb der Top 10)
#### F6 — Admin-Bereich
- Spielergebnisse manuell eintragen / korrigieren
- Punkte automatisch neu berechnen nach Eintrag
- Übersicht aller Tipps pro Spiel
- Teilnahme-Statistiken (Anzahl Tipps, aktive Nutzer)
### 3.2 Erweiterungen (Nice-to-have — v1.1 oder später)
| Feature | Beschreibung | Aufwand |
|---|---|---|
| **Push-Benachrichtigungen** | Ergebnisse-Update via Staffbase News API | Mittel |
| **Gruppenphase-Tipper** | Tipp auf Gruppensieger/-zweiten | Mittel |
| **Turniersieger-Tipp** | Einmaliger Tipp auf WM-Sieger (×5 Punkte) | Klein |
| **Mini-Ligen** | Interne Teams (z.B. nach Abteilung) | Groß |
| **Kommentar-Funktion** | Tipps kommentieren | Klein |
| **Tipp-Analyse** | Auswertung: beliebteste Tipps, Überraschungen | Mittel |
| **Automatische Ergebnis-Synchronisation** | Polling football-data.org, kein manuelles Eintragen | Mittel |
---
## 4. Datenbankschema
### 4.1 Kerntabellen
```sql
-- Nutzer (befüllt automatisch via JWT bei erstem Login)
CREATE TABLE users (
id VARCHAR(64) PRIMARY KEY, -- Staffbase userId
full_name VARCHAR(255) NOT NULL,
locale VARCHAR(10) DEFAULT 'de_DE',
role VARCHAR(20) DEFAULT 'reader',
branch_id VARCHAR(64),
created_at TIMESTAMPTZ DEFAULT NOW(),
last_seen_at TIMESTAMPTZ DEFAULT NOW()
);
-- WM-Spiele (synchronisiert via football-data.org)
CREATE TABLE matches (
id SERIAL PRIMARY KEY,
external_id VARCHAR(32) UNIQUE NOT NULL, -- ID aus football-data.org
stage VARCHAR(50) NOT NULL, -- 'GROUP_STAGE', 'ROUND_OF_16', ...
group_name VARCHAR(10), -- 'A', 'B', ... (NULL in KO-Runde)
home_team VARCHAR(100) NOT NULL,
away_team VARCHAR(100) NOT NULL,
kickoff_at TIMESTAMPTZ NOT NULL,
home_score SMALLINT, -- NULL bis Abpfiff
away_score SMALLINT,
status VARCHAR(20) DEFAULT 'SCHEDULED' -- SCHEDULED, IN_PLAY, FINISHED
);
-- Tipps
CREATE TABLE predictions (
id SERIAL PRIMARY KEY,
user_id VARCHAR(64) REFERENCES users(id),
match_id INTEGER REFERENCES matches(id),
predicted_home SMALLINT NOT NULL,
predicted_away SMALLINT NOT NULL,
points_earned SMALLINT, -- NULL bis Spiel ausgewertet
created_at TIMESTAMPTZ DEFAULT NOW(),
updated_at TIMESTAMPTZ DEFAULT NOW(),
UNIQUE (user_id, match_id)
);
-- Rangliste (materialized view oder separate Tabelle für Performance)
CREATE MATERIALIZED VIEW leaderboard AS
SELECT
u.id AS user_id,
u.full_name,
u.branch_id,
COALESCE(SUM(p.points_earned), 0) AS total_points,
COUNT(p.id) AS total_predictions,
COUNT(CASE WHEN p.points_earned = 3 THEN 1 END) AS exact_hits,
RANK() OVER (ORDER BY COALESCE(SUM(p.points_earned), 0) DESC) AS rank
FROM users u
LEFT JOIN predictions p ON p.user_id = u.id
GROUP BY u.id, u.full_name, u.branch_id;
```
---
## 5. API-Design (Backend)
### 5.1 Endpunkte
| Method | Endpunkt | Beschreibung | Auth |
|---|---|---|---|
| `GET` | `/api/matches` | Alle Spiele mit Status | JWT |
| `GET` | `/api/matches/:id` | Einzelnes Spiel | JWT |
| `GET` | `/api/predictions/me` | Eigene Tipps | JWT |
| `POST` | `/api/predictions` | Tipp abgeben | JWT |
| `PUT` | `/api/predictions/:id` | Tipp ändern (vor Deadline) | JWT |
| `GET` | `/api/leaderboard` | Gesamtrangliste | JWT |
| `GET` | `/api/leaderboard/me` | Eigene Position | JWT |
| `PUT` | `/api/admin/matches/:id/result` | Ergebnis eintragen | JWT + Admin |
| `POST` | `/api/admin/recalculate` | Punkte neu berechnen | JWT + Admin |
| `GET` | `/api/admin/stats` | Teilnahmestatistiken | JWT + Admin |
### 5.2 Authentifizierung
Jeder Request vom Frontend sendet den Staffbase JWT im Header:
```
Authorization: Bearer <staffbase-jwt-token>
```
Das Backend validiert den Token mit dem `@staffbase/staffbase-plugin-sdk` (RS256, Public Key aus Staffbase Studio). Bei gültigem Token werden Nutzer-ID, Name, Rolle und Locale aus dem Token extrahiert und der Nutzer automatisch in der `users`-Tabelle angelegt (upsert).
---
## 6. Projektphasen & Zeitplan
### Gesamtlaufzeit: 10 Wochen (April — Mitte Juni 2026)
### Phase 1 — Setup & Fundament (Woche 12)
| Aufgabe | Verantwortlich | Aufwand |
|---|---|---|
| Staffbase Plugin registrieren (Plugin-ID + Public Key) | Admin | 0,5 Tage |
| Node.js Projekt-Skeleton generieren (`create-staffbase-plugin-nodejs`) | Entwicklung | 0,5 Tage |
| Git-Repository anlegen, CI/CD konfigurieren (GitHub Actions) | Entwicklung | 1 Tag |
| Hosting-Umgebung aufsetzen (Railway/Render) | Entwicklung | 0,5 Tage |
| Supabase-Projekt anlegen, Datenbankschema deployen | Entwicklung | 1 Tag |
| JWT-Authentifizierung implementieren und testen | Entwicklung | 1 Tag |
| football-data.org API-Key beantragen und testen | Entwicklung | 0,5 Tage |
**Meilenstein:** Authentifizierter API-Call von Staffbase-Plugin zu Backend funktioniert.
### Phase 2 — Kern-Backend (Woche 34)
| Aufgabe | Verantwortlich | Aufwand |
|---|---|---|
| Spielplan-Synchronisation (football-data.org → DB) | Entwicklung | 2 Tage |
| REST API vollständig implementieren | Entwicklung | 3 Tage |
| Tipp-Logik mit Deadline-Prüfung | Entwicklung | 1 Tag |
| Punkte-Berechnungslogik | Entwicklung | 1 Tag |
| Ranglisten-Abfrage (inkl. Materialized View) | Entwicklung | 1 Tag |
| Unit-Tests für Kernlogik | Entwicklung | 1 Tag |
**Meilenstein:** Vollständige Backend-API testbar via Postman/API-Client.
### Phase 3 — Frontend (Woche 57)
| Aufgabe | Verantwortlich | Aufwand |
|---|---|---|
| React-Projekt aufsetzen, Staffbase Client SDK integrieren | Entwicklung | 1 Tag |
| Spielplan-Übersicht (nach Datum / Gruppe filtern) | Entwicklung | 2 Tage |
| Tipp-Eingabeformular mit Validierung | Entwicklung | 2 Tage |
| Rangliste mit Pagination | Entwicklung | 1,5 Tage |
| Admin-Bereich (Ergebnis eintragen, Statistiken) | Entwicklung | 2 Tage |
| Responsive Design (Mobile-first für Staffbase App) | Entwicklung | 1,5 Tage |
| Mehrsprachigkeit DE/EN | Entwicklung | 1 Tag |
**Meilenstein:** Vollständige App funktionsfähig im Browser (ohne Staffbase-Integration).
### Phase 4 — Staffbase-Integration & Test (Woche 89)
| Aufgabe | Verantwortlich | Aufwand |
|---|---|---|
| Plugin-URL in Staffbase Studio hinterlegen | Admin | 0,5 Tage |
| iFrame-Test in Staffbase Web und Mobile App | Entwicklung | 1 Tag |
| End-to-End-Tests mit echten Staffbase-Nutzern | Entwicklung + QA | 2 Tage |
| Bugfixing aus Testphase | Entwicklung | 2 Tage |
| Performance-Test (Last: viele gleichzeitige Tipps) | Entwicklung | 1 Tag |
| DSGVO-Check: keine unautorisierten Daten gespeichert | PM/Legal | 1 Tag |
**Meilenstein:** Plugin läuft stabil in der Staffbase-Staging-Umgebung.
### Phase 5 — Launch & Betrieb (Woche 10 + laufend)
| Aufgabe | Verantwortlich | Aufwand |
|---|---|---|
| Go-Live in Staffbase Produktivumgebung | Admin + Entwicklung | 1 Tag |
| Kommunikation an Mitarbeitende (via Staffbase News Channel) | Kommunikation | 0,5 Tage |
| Monitoring & Alerting einrichten (Uptime, Fehler-Logs) | Entwicklung | 1 Tag |
| WM-Start-Phase begleiten (Hotfixes, Support) | Entwicklung | laufend |
| Tägliche Ergebnispflege (manuell oder automatisch) | Admin | laufend |
---
## 7. Ressourcen & Rollen
| Rolle | Verantwortlichkeiten | Zeitaufwand |
|---|---|---|
| **Projektleiter/PM** | Steuerung, Stakeholder-Kommunikation, Abnahme | ~20% (verteilt) |
| **Fullstack-Entwickler (12)** | Backend, Frontend, Deployment, Tests | 100% über 8 Wochen |
| **Staffbase-Admin** | Plugin-Registrierung, Studio-Konfiguration, Rollout | ~5% |
| **Kommunikation** | Launch-Kommunikation, Mitarbeitende informieren | ~5% |
| **QA (optional)** | Testen, Bugmeldungen | ~20% in Phase 4 |
---
## 8. Infrastruktur & Kosten
### 8.1 Hosting (monatlich, geschätzt)
| Dienst | Zweck | Kosten/Monat |
|---|---|---|
| **Railway / Render** | Backend-Hosting (Node.js) | ~515 € |
| **Supabase** | PostgreSQL (Free Tier reicht für ~500 User) | 0 € (Free) / 25 € (Pro) |
| **football-data.org** | WM-Spielplan API | 0 € (Free Tier) |
| **GitHub** | Code-Repository + CI/CD | 0 € (Free) |
| **Gesamt** | | ~540 € / Monat |
### 8.2 Einmalige Kosten (Entwicklung)
Gemäß separater Aufwandsschätzung (siehe Projektphasen). Bei internem Entwicklerteam: reine Zeitkosten. Bei externer Vergabe: ca. 15.00025.000 € (je nach Erfahrungsniveau und Scope).
---
## 9. Risiken & Maßnahmen
| Risiko | Wahrscheinlichkeit | Auswirkung | Maßnahme |
|---|---|---|---|
| Staffbase JWT-Integration schlägt fehl | Niedrig | Hoch | Frühzeitig in Phase 1 testen, Staffbase Support einbinden |
| football-data.org API unzuverlässig | Mittel | Mittel | Spielplandaten lokal cachen, manuelle Eingabe als Fallback |
| Zu viele gleichzeitige Nutzer (WM-Start) | Mittel | Mittel | Load-Test vor Go-Live, Auto-Scaling auf Hosting-Plattform |
| DSGVO: unbeabsichtigte Datenspeicherung | Niedrig | Hoch | Nur JWT-Daten speichern, kein Tracking, Datenschutzprüfung |
| Entwicklungsrückstand (Urlaube, Krankheit) | Mittel | Mittel | Puffer von 1 Woche eingeplant, MVP-Scope reduzierbar |
| WM-Spielplan ändert sich (Absagen, Verlegungen) | Niedrig | Niedrig | Automatische API-Synchronisation |
---
## 10. Definition of Done (DoD)
Ein Feature gilt als fertig, wenn:
1. Funktionalität implementiert und manuell getestet
2. Unit-Tests vorhanden (Backend-Logik)
3. Responsive auf Mobile und Desktop
4. In Staffbase-iFrame getestet (Web + App)
5. Kein Fehler in den Browser-Konsolen-Logs
6. Code reviewed und in `main`-Branch gemergt
Das Gesamtprojekt gilt als abgenommen, wenn:
1. Alle MVP-Features (F1F6) funktionsfähig sind
2. Mind. 20 Test-Nutzer einen Tipp abgegeben haben (Pilottest)
3. Performance-Test bestanden (< 2 Sekunden Ladezeit)
4. DSGVO-Prüfung abgeschlossen und dokumentiert
5. Go-Live in Produktivumgebung erfolgt
---
## 11. Nächste Schritte (Sofortmaßnahmen)
1. **Plugin bei Staffbase registrieren** → Staffbase Studio → Einstellungen → Plugins → neues Plugin anlegen → Plugin-ID und Public Key notieren
2. **Entwicklungsumgebung aufsetzen**`npx create-staffbase-plugin-nodejs@latest wm2026-tippspiel`
3. **football-data.org API-Key beantragen** → https://www.football-data.org/client/register
4. **Supabase-Projekt anlegen** → https://supabase.com (EU-Region Frankfurt)
5. **Kickoff-Meeting** mit allen Beteiligten (PM, Entwicklung, Staffbase-Admin, Kommunikation)
---
## Anhang A: Nützliche Links & Ressourcen
| Ressource | URL |
|---|---|
| Staffbase Developer Portal | https://developers.staffbase.com |
| Staffbase Custom Plugin Übersicht | https://developers.staffbase.com/concepts/customplugin-overview/ |
| Staffbase Plugins Client SDK | https://github.com/Staffbase/plugins-client-sdk |
| Staffbase Node.js SDK | https://github.com/Staffbase/plugins-sdk-nodejs |
| Staffbase Plugin Skeleton Generator | https://github.com/Staffbase/create-staffbase-plugin-nodejs |
| football-data.org API | https://www.football-data.org |
| Supabase | https://supabase.com |
| Railway Hosting | https://railway.app |
| Render Hosting | https://render.com |
| WM 2026 Spielplan (FIFA) | https://www.fifa.com/worldcup |