# 💸 WhoPays - Who Pays Next?

Ein einfaches, elegantes Tool um zu entscheiden, wer als nächstes zahlt - mit Discord-Benachrichtigungen und PWA-Support!

![Version](https://img.shields.io/badge/version-1.0.0-blue)
![License](https://img.shields.io/badge/license-MIT-green)
![PWA](https://img.shields.io/badge/PWA-Ready-purple)

## 🎯 Features

- ✅ **Wechsel zwischen zwei Personen** - Einfacher Button-Klick
- 🎨 **Individuelle Farben & Namen** - Komplett anpassbar
- 📝 **Grund-Angabe** - Optional Grund für den Wechsel angeben
- 🔔 **Discord-Benachrichtigungen** - Automatische Webhooks mit farbigen Embeds
- 💾 **Persistenter Speicher** - Letzter Grund bleibt nach Container-Restart erhalten
- 📱 **PWA-Support** - Als App auf Handy & Desktop installierbar
- 🎭 **Animierte Übergänge** - Smooth Hintergrund- und Profilbild-Wechsel
- 🐳 **Docker-Ready** - Einfache Deployment mit Docker Compose
- 🔒 **Reverse-Proxy kompatibel** - Funktioniert mit Nginx, Caddy, Traefik, etc.

---

## 🚀 Quick Start

### Voraussetzungen

- Docker & Docker Compose
- Discord Webhook URL (optional)
- Profilbilder (a.png, b.png)
- Hintergrundbilder (bgA.jpg, bgB.jpg)

### Installation

```bash
# 1. Repository klonen oder Dateien herunterladen
git clone https://github.com/dein-username/whopays.git
cd whopays

# 2. Bilder hinzufügen
cp deine-bilder/* img/

# 3. config.js anpassen (siehe Konfiguration)
nano config.js

# 4. Docker Container starten
docker-compose up -d

# 5. Öffne http://localhost:3000
```

**Das war's!** 🎉

---

## ⚙️ Konfiguration

### config.js - Zentrale Konfiguration

Alle Einstellungen sind in **einer** Datei:

```javascript
// config.js
export const CONFIG = {
  A: {
    name: "Alice",              // Name Person A
    colorHex: "#2ecc71",        // Farbe im Web (Grün)
    colorDiscord: 0x2ecc71,     // Farbe in Discord (gleich!)
    icon: "a.png",              // Profilbild
    background: "bgA.jpg"       // Hintergrundbild
  },
  B: {
    name: "Bob",                // Name Person B
    colorHex: "#e74c3c",        // Farbe im Web (Rot)
    colorDiscord: 0xe74c3c,     // Farbe in Discord (gleich!)
    icon: "b.png",              // Profilbild
    background: "bgB.jpg"       // Hintergrundbild
  }
};

// Discord Webhook (optional)
export const DISCORD_WEBHOOK_URL = "https://discord.com/api/webhooks/...";

// Öffentliche URL (für Discord Thumbnails)
export const PUBLIC_BASE_URL = "https://your-domain.com";
```

### Farben ändern

```javascript
// Blau & Orange
A: { colorHex: "#3498db", colorDiscord: 0x3498db }
B: { colorHex: "#e67e22", colorDiscord: 0xe67e22 }

// Lila & Pink
A: { colorHex: "#9b59b6", colorDiscord: 0x9b59b6 }
B: { colorHex: "#e91e63", colorDiscord: 0xe91e63 }

// Türkis & Gold
A: { colorHex: "#1abc9c", colorDiscord: 0x1abc9c }
B: { colorHex: "#f39c12", colorDiscord: 0xf39c12 }
```

**Wichtig:** Hex-Farbe muss genau 6 Zeichen haben (0-9, A-F)!

---

## 📂 Projektstruktur

```
whopays/
├── config.js                 # Zentrale Konfiguration
├── server.js                 # Express Server
├── package.json              # Node.js Dependencies
├── Dockerfile               # Docker Build Instructions
├── docker-compose.yml       # Docker Compose Config
├── state.json              # Persistent State (auto-generiert)
│
└── public/                  # Statische Dateien
    ├── index.html          # Frontend HTML
    ├── script.js           # Frontend JavaScript
    ├── style.css           # CSS Animationen
    ├── manifest.json       # PWA Manifest
    ├── service-worker.js   # PWA Service Worker
    │
    └── img/                # Bilder
        ├── a.png           # Profilbild Person A
        ├── b.png           # Profilbild Person B
        ├── bgA.jpg         # Hintergrund Person A
        ├── bgB.jpg         # Hintergrund Person B
        ├── icon-192.png    # PWA Icon (192x192)
        └── icon-512.png    # PWA Icon (512x512)
```

---

## 🐳 Docker Deployment

### docker-compose.yml

```yaml
version: '3.8'

services:
  whopays:
    build: .
    ports:
      - "3000:3000"
    environment:
      - NODE_ENV=production
      - PORT=3000
      - PUBLIC_BASE_URL=https://your-domain.com
      - DISCORD_WEBHOOK_URL = "https://discord.com/api/webhooks/...";
    volumes:
      # Bilder (persistent)
      - ./img:/app/public/img
      
      # State (persistent über Neustarts)
      - ./state.json:/app/state.json
    
    restart: unless-stopped
```

### Befehle

```bash
# Container starten
docker-compose up -d

# Logs anschauen
docker-compose logs -f

# Container neustarten
docker-compose restart

# Container stoppen
docker-compose down

# Neu bauen (nach Code-Änderungen)
docker-compose down
docker-compose build --no-cache
docker-compose up -d
```

---

## 📱 PWA Installation

### iOS (Safari)

1. Öffne die Website in Safari
2. Tippe auf das **Teilen**-Symbol (⎙)
3. Scrolle und tippe **"Zum Home-Bildschirm"**
4. Tippe **"Hinzufügen"**

### Android (Chrome)

1. Öffne die Website in Chrome
2. Tippe auf **Menü** (⋮)
3. Tippe **"App installieren"**
4. Tippe **"Installieren"**

### Desktop (Chrome/Edge)

1. Öffne die Website
2. Klicke auf das **⊕ Icon** in der Adressleiste
3. Oder: Menü → "WhoPays installieren"

**Wichtig:** PWA funktioniert nur über HTTPS (oder localhost)!

---

## 🔒 Reverse Proxy Setup

### Nginx

```nginx
server {
    listen 443 ssl http2;
    server_name whopays.your-domain.com;
    
    # PWA Files - NO AUTH
    location ~ ^/(service-worker\.js|manifest\.json)$ {
        proxy_pass http://localhost:3000;
        proxy_set_header X-Forwarded-Proto $scheme;
        add_header Service-Worker-Allowed "/" always;
    }
    
    # Main app
    location / {
        proxy_pass http://localhost:3000;
        proxy_set_header Host $host;
        proxy_set_header X-Forwarded-Proto $scheme;
    }
}
```

### Caddy (Einfachste Option!)

```caddy
whopays.your-domain.com {
    reverse_proxy localhost:3000
}
```

Caddy macht automatisch HTTPS mit Let's Encrypt! ✅

---

## 🔧 API Endpoints

### GET /status

```bash
curl http://localhost:3000/status
```

Response:
```json
{
  "current": "A",
  "lastReason": "Pizza bestellt"
}
```

### POST /toggle

```bash
curl -X POST http://localhost:3000/toggle \
  -H "Content-Type: application/json" \
  -d '{"reason":"Kaffee trinken"}'
```

Response:
```json
{
  "current": "B",
  "name": "Bob",
  "lastReason": "Kaffee trinken"
}
```

### GET /config

```bash
curl http://localhost:3000/config
```

---

## 🐛 Troubleshooting

### PWA lässt sich nicht installieren

- Stelle sicher, dass du HTTPS verwendest
- Prüfe ob `manifest.json` erreichbar ist
- Icons müssen existieren: `icon-192.png` und `icon-512.png`

### Discord sendet keine Benachrichtigungen

- Prüfe Webhook URL in `config.js`
- Logs prüfen: `docker-compose logs | grep Discord`
- Stelle sicher `PUBLIC_BASE_URL` ist korrekt

### Bilder werden nicht angezeigt

- Prüfe ob Bilder in `/img/` existieren
- Berechtigungen: `chmod -R 755 img/`
- Container neu starten

### Farbe in Discord ungültig (HTTP 400)

- Hex-Farbe muss genau 6 Zeichen haben
- ✅ Richtig: `0x2ecc71`
- ❌ Falsch: `0x2ecc71c` (extra Buchstabe!)

---

## 📊 Features im Detail

### Persistent Storage

```json
{
  "current": "A",
  "lastReason": "Restaurant bezahlt"
}
```

Bleibt erhalten durch Docker Volume Mount.

### Smooth Animations

- Rotation-Animation (0.6s)
- Background-Transition (0.6s)
- Farb-Übergang (0.3s)
- Image Preloading

---

## 📜 Lizenz

MIT License - Frei nutzbar!

---

## 💡 Tipps

### Custom Domain mit Let's Encrypt

```bash
sudo certbot --nginx -d whopays.your-domain.com
```

### Mehrere Instanzen

Unterschiedliche Ports in docker-compose.yml für mehrere Apps!

---

**Viel Spaß beim Entscheiden, wer zahlt!** 🎉💸
S
Description
Docker Container um zu zeigen wer zahlen muss
Readme
3.9 MiB
0 Stars 0 Watchers 0 Forks
Languages
JavaScript 78.2%
HTML 17.2%
CSS 3.2%
Dockerfile 1.4%