Docker Compose with 24+ services: - PostgreSQL (PostGIS), Valkey, MinIO, Qdrant - Vault (PKI/TLS), Nginx (Reverse Proxy) - Backend Core API, Consent Service, Billing Service - RAG Service, Embedding Service - Gitea, Woodpecker CI/CD - Night Scheduler, Health Aggregator - Jitsi (Web/XMPP/JVB/Jicofo), Mailpit Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
22 KiB
22 KiB
RAG & Daten-Management Spezifikation
Übersicht
Admin-Frontend für die Verwaltung von Trainingsdaten und RAG-Systemen in BreakPilot.
Location: /admin/docs → Tab "Daten & RAG"
Backend: klausur-service (Port 8086)
Storage: MinIO (persistentes Docker Volume minio_data)
Vector DB: Qdrant (Port 6333)
Datenmodell
Zwei Datentypen mit unterschiedlichen Regeln
| Typ | Quelle | Training erlaubt | Isolation | Collection |
|---|---|---|---|---|
| Landes-Daten | NiBiS, andere Bundesländer | ✅ Ja | Pro Bundesland | bp_{bundesland}_{usecase} |
| Lehrer-Daten | Lehrer-Upload (BYOEH) | ❌ Nein | Pro Tenant (Schule/Lehrer) | bp_eh (verschlüsselt) |
Bundesland-Codes (ISO 3166-2:DE)
NI = Niedersachsen BY = Bayern BW = Baden-Württemberg
NW = Nordrhein-Westf. HE = Hessen SN = Sachsen
BE = Berlin HH = Hamburg SH = Schleswig-Holstein
BB = Brandenburg MV = Meckl.-Vorp. ST = Sachsen-Anhalt
TH = Thüringen RP = Rheinland-Pfalz SL = Saarland
HB = Bremen
Use Cases (RAG-Sammlungen)
| Use Case | Collection Pattern | Beschreibung |
|---|---|---|
| Klausurkorrektur | bp_{bl}_klausur |
Erwartungshorizonte für Abitur |
| Zeugnisgenerator | bp_{bl}_zeugnis |
Textbausteine für Zeugnisse |
| Lehrplan | bp_{bl}_lehrplan |
Kerncurricula, Rahmenrichtlinien |
Beispiel: bp_ni_klausur = Niedersachsen Klausurkorrektur
MinIO Bucket-Struktur
breakpilot-rag/
├── landes-daten/
│ ├── ni/ # Niedersachsen
│ │ ├── klausur/
│ │ │ ├── 2016/
│ │ │ │ ├── manifest.json
│ │ │ │ └── *.pdf
│ │ │ ├── 2017/
│ │ │ ├── ...
│ │ │ └── 2025/
│ │ └── zeugnis/
│ ├── by/ # Bayern
│ └── .../
│
└── lehrer-daten/ # BYOEH - verschlüsselt
└── {tenant_id}/
└── {lehrer_id}/
└── *.pdf.enc
Qdrant Schema
Landes-Daten Collection (z.B. bp_ni_klausur)
{
"id": "uuid-v5-from-string",
"vector": [384 dimensions],
"payload": {
"original_id": "nibis_2024_deutsch_ea_1_abc123_chunk_0",
"doc_id": "nibis_2024_deutsch_ea_1_abc123",
"chunk_index": 0,
"text": "Der Erwartungshorizont...",
"year": 2024,
"subject": "Deutsch",
"niveau": "eA",
"task_number": 1,
"doc_type": "EWH",
"bundesland": "NI",
"source": "nibis",
"training_allowed": true,
"minio_path": "landes-daten/ni/klausur/2024/2024_Deutsch_eA_I_EWH.pdf"
}
}
Lehrer-Daten Collection (bp_eh)
{
"id": "uuid",
"vector": [384 dimensions],
"payload": {
"tenant_id": "schule_123",
"eh_id": "eh_abc",
"chunk_index": 0,
"subject": "deutsch",
"encrypted_content": "base64...",
"training_allowed": false
}
}
Frontend-Komponenten
1. Sammlungen-Übersicht (/admin/rag/collections)
┌─────────────────────────────────────────────────────────────────┐
│ Daten & RAG │
├─────────────────────────────────────────────────────────────────┤
│ │
│ Sammlungen [+ Neu] │
│ ───────────────────────────────────────────────────────────── │
│ │
│ ┌─────────────────────────────────────────────────────────┐ │
│ │ 📚 Niedersachsen - Klausurkorrektur │ │
│ │ bp_ni_klausur | 630 Docs | 4.521 Chunks | 2016-2025 │ │
│ │ [Suchen] [Indexieren] [Details] │ │
│ └─────────────────────────────────────────────────────────┘ │
│ │
│ ┌─────────────────────────────────────────────────────────┐ │
│ │ 📚 Niedersachsen - Zeugnisgenerator │ │
│ │ bp_ni_zeugnis | 0 Docs | Leer │ │
│ │ [Suchen] [Indexieren] [Details] │ │
│ └─────────────────────────────────────────────────────────┘ │
│ │
└─────────────────────────────────────────────────────────────────┘
2. Upload-Bereich (/admin/rag/upload)
┌─────────────────────────────────────────────────────────────────┐
│ Dokumente hochladen │
├─────────────────────────────────────────────────────────────────┤
│ │
│ Ziel-Sammlung: [Niedersachsen - Klausurkorrektur ▼] │
│ │
│ ┌─────────────────────────────────────────────────────────┐ │
│ │ │ │
│ │ 📁 ZIP-Datei oder Ordner hierher ziehen │ │
│ │ │ │
│ │ oder [Dateien auswählen] │ │
│ │ │ │
│ │ Unterstützt: .zip, .pdf, Ordner │ │
│ │ │ │
│ └─────────────────────────────────────────────────────────┘ │
│ │
│ Upload-Queue: │
│ ┌─────────────────────────────────────────────────────────┐ │
│ │ ✅ 2018.zip - 45 PDFs erkannt │ │
│ │ ⏳ 2019.zip - Wird analysiert... │ │
│ └─────────────────────────────────────────────────────────┘ │
│ │
│ [Hochladen & Indexieren] │
│ │
└─────────────────────────────────────────────────────────────────┘
3. Ingestion-Status (/admin/rag/ingestion)
┌─────────────────────────────────────────────────────────────────┐
│ Ingestion Status │
├─────────────────────────────────────────────────────────────────┤
│ │
│ Aktueller Job: Niedersachsen Klausur 2024 │
│ ████████████████████░░░░░░░░░░ 65% (412/630 Docs) │
│ Chunks: 2.891 | Fehler: 3 | ETA: 4:32 │
│ [Pausieren] [Abbrechen] │
│ │
│ ───────────────────────────────────────────────────────────── │
│ │
│ Letzte Jobs: │
│ ┌─────────────────────────────────────────────────────────┐ │
│ │ ✅ 09.01.2025 15:30 - NI Klausur 2024 - 128 Chunks │ │
│ │ ✅ 09.01.2025 14:00 - NI Klausur 2017 - 890 Chunks │ │
│ │ ❌ 08.01.2025 10:15 - BY Klausur - Fehler: Timeout │ │
│ └─────────────────────────────────────────────────────────┘ │
│ │
└─────────────────────────────────────────────────────────────────┘
4. Suche & Qualitätstest (/admin/rag/search)
┌─────────────────────────────────────────────────────────────────┐
│ RAG Suche & Qualitätstest │
├─────────────────────────────────────────────────────────────────┤
│ │
│ Sammlung: [Niedersachsen - Klausurkorrektur ▼] │
│ │
│ Query: [Analyse eines Gedichts von Rilke ] │
│ │
│ Filter: │
│ Jahr: [Alle ▼] Fach: [Deutsch ▼] Niveau: [eA ▼] │
│ │
│ [🔍 Suchen] │
│ │
│ ───────────────────────────────────────────────────────────── │
│ │
│ Ergebnisse (3): Latenz: 45ms │
│ │
│ ┌─────────────────────────────────────────────────────────┐ │
│ │ #1 | Score: 0.847 | 2024 Deutsch eA Aufgabe 2 │ │
│ │ │ │
│ │ "...Die Analyse des Rilke-Gedichts soll folgende │ │
│ │ Aspekte berücksichtigen: Aufbau, Bildsprache..." │ │
│ │ │ │
│ │ Relevanz: [⭐⭐⭐⭐⭐] [⭐⭐⭐⭐] [⭐⭐⭐] [⭐⭐] [⭐] │ │
│ │ Notizen: [Optional: Warum relevant/nicht relevant? ] │ │
│ └─────────────────────────────────────────────────────────┘ │
│ │
└─────────────────────────────────────────────────────────────────┘
5. Metriken-Dashboard (/admin/rag/metrics)
┌─────────────────────────────────────────────────────────────────┐
│ RAG Qualitätsmetriken │
├─────────────────────────────────────────────────────────────────┤
│ │
│ Zeitraum: [Letzte 7 Tage ▼] Sammlung: [Alle ▼] │
│ │
│ ┌──────────────┐ ┌──────────────┐ ┌──────────────┐ │
│ │ Precision@5 │ │ Recall@10 │ │ MRR │ │
│ │ 0.78 │ │ 0.85 │ │ 0.72 │ │
│ │ ↑ +5% │ │ ↑ +3% │ │ ↓ -2% │ │
│ └──────────────┘ └──────────────┘ └──────────────┘ │
│ │
│ ┌──────────────┐ ┌──────────────┐ ┌──────────────┐ │
│ │ Avg Latency │ │ Bewertungen │ │ Fehlerrate │ │
│ │ 52ms │ │ 127 │ │ 0.3% │ │
│ └──────────────┘ └──────────────┘ └──────────────┘ │
│ │
│ ───────────────────────────────────────────────────────────── │
│ │
│ Score-Verteilung: │
│ 0.9+ ████████████████ 23% │
│ 0.7+ ████████████████████████████ 41% │
│ 0.5+ ████████████████████ 28% │
│ <0.5 ██████ 8% │
│ │
│ [Export CSV] [Detailbericht] │
│ │
└─────────────────────────────────────────────────────────────────┘
API Endpoints
Collections API
GET /api/v1/admin/rag/collections
POST /api/v1/admin/rag/collections
GET /api/v1/admin/rag/collections/{id}
DELETE /api/v1/admin/rag/collections/{id}
GET /api/v1/admin/rag/collections/{id}/stats
Upload API
POST /api/v1/admin/rag/upload
Content-Type: multipart/form-data
- file: ZIP oder PDF
- collection_id: string
- metadata: JSON (optional)
POST /api/v1/admin/rag/upload/folder
- Für Ordner-Upload (WebKitDirectory)
Ingestion API
POST /api/v1/admin/rag/ingest
- collection_id: string
- filters: {year?, subject?, doc_type?}
GET /api/v1/admin/rag/ingest/status
GET /api/v1/admin/rag/ingest/history
POST /api/v1/admin/rag/ingest/cancel
Search API
POST /api/v1/admin/rag/search
- query: string
- collection_id: string
- filters: {year?, subject?, niveau?}
- limit: int
POST /api/v1/admin/rag/search/feedback
- result_id: string
- rating: 1-5
- notes: string (optional)
Metrics API
GET /api/v1/admin/rag/metrics
- collection_id?: string
- from_date?: date
- to_date?: date
GET /api/v1/admin/rag/metrics/export
- format: csv|json
Embedding-Konfiguration
# Default: Lokale Embeddings (kein API-Key nötig)
EMBEDDING_BACKEND = "local"
LOCAL_EMBEDDING_MODEL = "all-MiniLM-L6-v2"
VECTOR_DIMENSIONS = 384
# Optional: OpenAI (für Produktion)
EMBEDDING_BACKEND = "openai"
EMBEDDING_MODEL = "text-embedding-3-small"
VECTOR_DIMENSIONS = 1536
Datenpersistenz
Docker Volumes (WICHTIG - nicht löschen!)
volumes:
minio_data: # Alle hochgeladenen Dokumente
qdrant_data: # Alle Vektoren und Embeddings
postgres_data: # Metadaten, Bewertungen, History
Backup-Strategie
# MinIO Backup
docker exec breakpilot-pwa-minio mc mirror /data /backup
# Qdrant Backup
curl -X POST http://localhost:6333/collections/bp_ni_klausur/snapshots
# Postgres Backup (bereits implementiert)
# Läuft automatisch täglich um 2 Uhr
Implementierungsreihenfolge
- ✅ Backend: Basis-Ingestion (nibis_ingestion.py)
- ✅ Backend: Lokale Embeddings (sentence-transformers)
- ✅ Backend: MinIO-Integration (minio_storage.py)
- ✅ Backend: Collections API (admin_api.py)
- ✅ Backend: Upload API mit ZIP-Support
- ✅ Backend: Metrics API mit PostgreSQL (metrics_db.py)
- ✅ Frontend: Sammlungen-Übersicht
- ✅ Frontend: Upload-Bereich (Drag & Drop)
- ✅ Frontend: Ingestion-Status
- ✅ Frontend: Suche & Qualitätstest (mit Stern-Bewertungen)
- ✅ Frontend: Metriken-Dashboard
Technologie-Stack
- Frontend: Next.js 15 (
/website/app/admin/rag/page.tsx) - Backend: FastAPI (
klausur-service/backend/) - Vector DB: Qdrant v1.7.4 (384-dim Vektoren)
- Object Storage: MinIO (S3-kompatibel)
- Embeddings: sentence-transformers
all-MiniLM-L6-v2 - Metrics DB: PostgreSQL 16
Entwickler-Dokumentation
Projektstruktur
klausur-service/
├── backend/
│ ├── main.py # FastAPI App + BYOEH Endpoints
│ ├── admin_api.py # RAG Admin API (Upload, Search, Metrics)
│ ├── nibis_ingestion.py # NiBiS Dokument-Ingestion Pipeline
│ ├── eh_pipeline.py # Chunking, Embeddings, Encryption
│ ├── qdrant_service.py # Qdrant Client + Search
│ ├── minio_storage.py # MinIO S3 Storage
│ ├── metrics_db.py # PostgreSQL Metrics
│ ├── requirements.txt # Python Dependencies
│ └── tests/
│ └── test_rag_admin.py
└── docs/
└── RAG-Admin-Spec.md # Diese Datei
Schnellstart für Entwickler
# 1. Services starten
cd /path/to/breakpilot-pwa
docker-compose up -d qdrant minio postgres
# 2. Dependencies installieren
cd klausur-service/backend
pip install -r requirements.txt
# 3. Service starten
python -m uvicorn main:app --port 8086 --reload
# 4. RAG-Services initialisieren (erstellt Bucket + Tabellen)
curl -X POST http://localhost:8086/api/v1/admin/rag/init
API-Referenz (Implementiert)
NiBiS Ingestion
GET /api/v1/admin/nibis/discover # Dokumente finden
POST /api/v1/admin/nibis/ingest # Indexierung starten
GET /api/v1/admin/nibis/status # Status abfragen
GET /api/v1/admin/nibis/stats # Statistiken
POST /api/v1/admin/nibis/search # Semantische Suche
GET /api/v1/admin/nibis/collections # Qdrant Collections
RAG Upload & Storage
POST /api/v1/admin/rag/upload # ZIP/PDF hochladen
GET /api/v1/admin/rag/upload/history # Upload-Verlauf
GET /api/v1/admin/rag/storage/stats # MinIO Statistiken
Metrics & Feedback
GET /api/v1/admin/rag/metrics # Qualitätsmetriken
POST /api/v1/admin/rag/search/feedback # Bewertung abgeben
POST /api/v1/admin/rag/init # Services initialisieren
Umgebungsvariablen
# Qdrant
QDRANT_URL=http://localhost:6333
# MinIO
MINIO_ENDPOINT=localhost:9000
MINIO_ACCESS_KEY=breakpilot
MINIO_SECRET_KEY=breakpilot123
MINIO_BUCKET=breakpilot-rag
# PostgreSQL
DATABASE_URL=postgres://breakpilot:breakpilot123@localhost:5432/breakpilot_db
# Embeddings
EMBEDDING_BACKEND=local
LOCAL_EMBEDDING_MODEL=all-MiniLM-L6-v2
Aktuelle Indexierungs-Statistik
- Dokumente: 579 Erwartungshorizonte (NiBiS)
- Chunks: 7.352
- Jahre: 2016, 2017, 2024, 2025
- Fächer: Deutsch, Englisch, Mathematik, Physik, Chemie, Biologie, Geschichte, Politik-Wirtschaft, Erdkunde, Sport, Kunst, Musik, Latein, Informatik, Ev. Religion, Kath. Religion, Werte und Normen, etc.
- Collection:
bp_nibis_eh - Vektor-Dimensionen: 384