# WatchStack > **v0.5.0-beta** — eine Watchlist für **Bücher, Serien & mehr** — inspiriert von MyAnimeList, aber mit eigenem Konzept. [![License: Apache-2.0](https://img.shields.io/badge/License-Apache_2.0-blue.svg)](https://www.apache.org/licenses/LICENSE-2.0) [![Repo](https://img.shields.io/badge/repo-Vibecode%2Fwatchlist-blue)](https://git.pkop.de/Vibecode/watchlist) [![Python 3.11+](https://img.shields.io/badge/python-3.11%2B-blue)](https://www.python.org) [![Docker](https://img.shields.io/badge/docker-ready-blue)](#-docker) WatchStack ist eine **single-user-lokale** Watchlist-App. Bücher und Serien teilen sich eine Oberfläche, ein Datenmodell und eine Such- und Filterlogik. Keine Anmeldung, kein Cloud-Zwang — läuft komplett auf deiner Maschine oder in einem Docker-Container. ## ✨ Features - 📚 **Bücher**: Titel, Autor, Bände / Kapitel / Seiten, ISBN, Cover via Open Library - 📺 **Serien**: Staffeln, Episoden, Sender / Streaming, Sendezeitraum, Cover-URL - 🗂 **Status**: Plan · Laufend · Abgeschlossen · Pausiert · Abgebrochen (5 Stufen, MAL-ähnlich) - ⭐ **Bewertungen** 1–10 mit Auto-Status: 0% → Plan, 100% → Done (+ `end_date`) - 🔎 **Suche & Filter**: Volltext, Status, Genre, Tag, Sortierung - 📊 **Dashboard**: Verteilung pro Medium, Durchschnittsbewertung - 🏷 **Genres & Tags** frei verwaltbar - 🌙 **Dark Theme** Default, modernes UI mit Hero + Drawer + Modals - 🐳 **Docker-ready**: Multi-stage Build, non-root, gunicorn + uvicorn-Worker, healthcheck - 🌐 **CORS offen** für lokale Entwicklung; in Produktion via Reverse-Proxy einschränken ## ⚠️ Beta-Hinweis **v0.5.0-beta** bedeutet: - Kernfunktionalität (CRUD, Suche, Stats, Progress) ist stabil und getestet - Datenmodell kann sich noch ändern (siehe `models.py` — additive Änderungen wahrscheinlich) - Datenbank-Migrationen sind **nicht** enthalten — bei Major-Upgrades DB sichern - Public-API-Pfade stabil; Sub-Ressourcen (Genres/Tags) noch in Bewegung Bitte Issues und Wünsche im [Repo](https://git.pkop.de/Vibecode/watchlist) melden. ## 🚀 Quickstart ### Option A: Docker (empfohlen) ```bash docker compose up -d # → http://localhost:8000 # Oder direkt: docker build -t watchstack:beta . docker run -d --name watchstack -p 8000:8000 -v watchstack-data:/data watchstack:beta ``` Die SQLite-DB liegt im benannten Volume `watchstack-data` (Pfad `/data/watchstack.db` im Container). Backups: `docker run --rm -v watchstack-data:/data -v $PWD:/backup alpine tar czf /backup/ws-$(date +%F).tgz /data`. ### Option B: Lokal (Python 3.11+) ```bash git clone https://git.pkop.de/Vibecode/watchlist.git cd watchlist ./run.sh # legt venv an, installiert deps, startet auf 127.0.0.1:8000 ``` ### Option C: Manuell ```bash python3 -m venv .venv source .venv/bin/activate pip install -r requirements.txt uvicorn app.main:app --reload ``` ## 🔧 Konfiguration (Umgebungsvariablen) | Variable | Default | Zweck | |---|---|---| | `WATCHSTACK_DATA_DIR` | `./data` | Pfad für SQLite-DB (im Container: `/data`) | | `WATCHSTACK_HOST` | `127.0.0.1` | Bind-Adresse (Docker: `0.0.0.0`) | | `WATCHSTACK_PORT` | `8000` | HTTP-Port | | `WATCHSTACK_WORKERS` | `2` | gunicorn-Worker (nur Docker) | | `WATCHSTACK_HTTP_TIMEOUT` | `8` | Timeout für Open-Library-Lookup (Sek.) | ## 📚 API-Übersicht | Methode | Pfad | Zweck | |---|---|---| | GET | `/api/health` | Service-Info + Version | | GET | `/api/media` | Liste, Filter via Query-Params | | POST | `/api/media` | Anlegen (201) | | GET | `/api/media/{id}` | Detail | | PATCH | `/api/media/{id}` | Teil-Update | | DELETE | `/api/media/{id}` | Löschen (204) | | POST | `/api/media/{id}/progress` | `{"delta":1}` oder `{"set_to":N}` | | GET | `/api/genres`, `/api/tags` | Taxonomien | | GET | `/api/stats` | Verteilungen + ⌀-Bewertung | | GET | `/api/lookup/book?isbn=…` | Cover via Open Library | **Beispiel** — neuen Eintrag anlegen: ```bash curl -X POST http://localhost:8000/api/media \ -H 'Content-Type: application/json' \ -d '{ "kind": "book", "title": "Der Name des Windes", "author": "Patrick Rothfuss", "total_pages": 662, "pages_read": 100, "status": "reading", "rating": 9.0, "genres": ["Fantasy"], "tags": ["Königsmörder"] }' ``` Vollständige interaktive Doku: (Swagger UI, von FastAPI generiert). ## 🏗 Projektstruktur ``` watchlist/ ├── app/ │ ├── __init__.py # __version__ │ ├── main.py # FastAPI-App + Routen │ ├── database.py # Engine + Session │ ├── models.py # SQLAlchemy-Modelle │ ├── schemas.py # Pydantic-Schemas │ ├── crud.py # DB-Operationen │ ├── external.py # Open-Library-Client │ ├── seed.py # Demo-Daten │ └── static/ # Frontend (HTML/CSS/JS) ├── data/ # SQLite-DB (gitignored, Volume im Container) ├── .github/workflows/ # CI ├── Dockerfile # Multi-stage Build ├── docker-compose.yml ├── LICENSE # Apache-2.0 (offizieller Volltext) ├── NOTICE # Copyright + Drittanbieter └── README.md ``` ## 🛠 Entwicklung ```bash # Tests (bisher Smoke-Tests ad-hoc; pytest-Suite ist Roadmap) python -c "from app.main import app; print(app.title, app.version)" # Code-Style ruff check app/ # (optional, nicht in requirements) ``` ## 📜 Lizenz **Apache License 2.0** — siehe [LICENSE](./LICENSE) (vollständiger Text) und [NOTICE](./NOTICE) (Drittanbieter-Hinweise). Kurzfassung: Du darfst das Projekt privat und kommerziell nutzen, verändern, weitergeben — unter Beibehaltung des Copyright-Hinweises und der Lizenz. Es gibt **keine** Patent-Gewähr; Änderungen müssen markiert werden. Volltext in der LICENSE-Datei. ## 🤝 Contributing PRs willkommen — am besten mit Issue vorab. Bitte: - Coding-Style einhalten (PEP 8, KISS, DRY) - Keine externen Tracker; Issues im Gitea-Repo - Tests für neue Logik (pytest-Suite kommt) ## 🔮 Roadmap - [ ] pytest-Suite mit Coverage-Report - [ ] Backup-/Restore-Endpoint - [ ] Import von MAL-XML / Trakt-Listen - [ ] Manga als dritte Medienart (Volumes, Chapters) - [ ] Multi-User mit OIDC-Login (optional, hinter Feature-Flag) - [ ] Cover-Caching-Proxy - [ ] Deutsche Übersetzungen der Status-Labels i18n-ready