update
This commit is contained in:
@@ -1,4 +1,5 @@
|
||||
import asyncio
|
||||
import json
|
||||
import shutil
|
||||
import uuid
|
||||
from datetime import datetime, timezone
|
||||
@@ -45,6 +46,38 @@ async def get_topics():
|
||||
return db_topics + sorted(derived - set(db_topics))
|
||||
|
||||
|
||||
@router.get("/stats")
|
||||
async def get_stats():
|
||||
"""Tracker: Themen-Anzahl + pro Format erstellt/absolviert (alle Kapitel abgehakt)."""
|
||||
guides = await list_guides()
|
||||
themen = set(await db_list_topics()) | {g["topic"] for g in guides} | set(bausteine_topics())
|
||||
if PROJECTS_DIR.is_dir():
|
||||
themen |= {e.name for e in PROJECTS_DIR.iterdir() if e.is_dir()}
|
||||
|
||||
formate = {}
|
||||
for fmt in ("MiniGuide", "Guide", "FullGuide"):
|
||||
# Pro Thema zählt nur der neueste fertige Guide (Altläufe teilen die Content-Datei)
|
||||
neueste: dict[str, dict] = {}
|
||||
for g in guides:
|
||||
if g["format"] == fmt and g["status"] == "done":
|
||||
if g["topic"] not in neueste or g["created_at"] > neueste[g["topic"]]["created_at"]:
|
||||
neueste[g["topic"]] = g
|
||||
absolviert = 0
|
||||
for g in neueste.values():
|
||||
path = guide_content_path(g["topic"], fmt)
|
||||
if not path.exists():
|
||||
continue
|
||||
try:
|
||||
chapters = json.loads(path.read_text(encoding="utf-8")).get("chapters", [])
|
||||
except ValueError:
|
||||
continue
|
||||
titles = {c.get("title") for c in chapters}
|
||||
if titles and titles <= set(await list_progress(g["id"])):
|
||||
absolviert += 1
|
||||
formate[fmt] = {"erstellt": len(neueste), "absolviert": absolviert}
|
||||
return {"themen": len(themen), "formate": formate}
|
||||
|
||||
|
||||
@router.post("/topics")
|
||||
async def add_topic(req: TopicCreateRequest):
|
||||
await create_topic(req.name.strip())
|
||||
|
||||
Reference in New Issue
Block a user