173 lines
8.8 KiB
Markdown
173 lines
8.8 KiB
Markdown
# NSCT – Handoff für neue Threads
|
||
|
||
> Diese Datei wird **nicht** in Git gepushed. Sie dient nur als Brücke zwischen Threads.
|
||
|
||
---
|
||
|
||
## Projekt: NSCT – Neutral Search Crawler Tool
|
||
|
||
**Ziel:** Vollständig lokal betreibbares, containerisiertes Recherche- und Analyse-System.
|
||
Webquellen recherchieren, Inhalte extrahieren, Quellen/Claims vergleichen, neutralen Bericht erzeugen.
|
||
|
||
**Repository:** `https://git.frerkc.de/opencode/NSCT---Neutral-Search-Crawler-Tool.git`
|
||
**Branch:** `main` — alle Commits sind bereits gepusht.
|
||
|
||
---
|
||
|
||
## Bisher abgeschlossene Stages
|
||
|
||
| Stage | Beschreibung | Commit | Files | Tests |
|
||
|---|---|---|---|---|
|
||
| 0 | Repository & Architekturgrundlage | `e9410be` | 28 | 6 |
|
||
| 1 | Model Provider Layer (LLM/Vision/Audio, Metriken, Debug) | `9280d69` | 6 | – |
|
||
| 2 | Search Provider Abstraction (DuckDuckGo, Multi-Provider, POST /search) | `a1ef260` | 5 | 25 |
|
||
| 3 | Crawler & Content Extraction (SSRF, trafilatura, PDF, Batch) | `a8595cc` | 10 | ~15 |
|
||
| 4 | Research Planner (LLM-basierte Recherchestrategie, Search-Bias-Reduktion) | `b8181de` | 6 | 25 |
|
||
| 5 | Claim Extraction (atomare, überprüfbare Claims mit Provenance) | `e8b6515` | 7 | 36 |
|
||
| 6 | Source Independence & Citation Graph (Syndication-Erkennung, similarity) | `a60cf21` | 4 | 43 |
|
||
| 7 | Claim Clustering & Contradiction Candidates (LLM-Clustering, numerische Normalisierung) | `d1e6bb6` | 6 | 79 |
|
||
| 8 | Evidence Scoring (6-dimensionale Scores, evidence_type, raw_scores_json) | `719e218` | 6 | ~60 |
|
||
| 9 | Neutral Synthesis Engine | `d87e2b4` | 1 | 25 |
|
||
| 10 | Vision Integration — Qwen2.5-VL-3B für Diagramme, Screenshots, Infografiken, PDF-Layouts | `3ab875d` | 6 | ~25 |
|
||
|| 11 | Audio Integration — STT-Transkription mit timestamped Claims | `10a083a` | 8 | ~20 |
|
||
||| 12 | **Research Orchestrator** — State Machine + Budget Limits + Pipeline-Steuerung | `2ef7b67` | 4 | 0 |
|
||
||| 13 | **Iterative Research / Gap Analysis** — Lückenerkennung, max 3 Runden, GapSearchQuery | `0b7a624` | 5 | 17 |
|
||
||| **14** | ~~REST API~~ (✅ **ABGESCHLOSSEN** — `rest_research.py` + `main.py` + `tests/test_rest_research.py`) |
|
||
||| **15** | ~~CLI~~ (✅ **ABGESCHLOSSEN** — `cli.py` + `tests/test_cli.py`) |
|
||
||| **16** | ~~Observability~~ (✅ **ABGESCHLOSSEN** — `logging_config.py` + `metrics.py` + `test_logging.py` + `test_metrics.py`) |
|
||
|
||
**Gesamt:** ~100 Dateien, ~17050 Zeilen Code, ~380 Tests.
|
||
|
||
---
|
||
|
||
## Stage 12 – Research Orchestrator (abgeschlossen)
|
||
|
||
Implementiert die zentrale Orchestrator-Klasse, die alle Stages (1–11) verbindet.
|
||
|
||
### Kernkomponenten
|
||
|
||
**`src/nsct/orchestration/state.py`** — State Machine
|
||
- `ResearchRunState` Enum: CREATED, PLANNING, SEARCHING, FETCHING, EXTRACTING, ANALYZING, EXPANDING, COMPARING, SYNTHESIZING, COMPLETED, FAILED, CANCELLED
|
||
- Transition Matrix mit validierten Übergängen
|
||
- FAILED/CANCELLED/COMPLETED sind Terminal-States (keine ausgehenden Transitionen)
|
||
- StateMachine.transition(new_state) mit Logging und Validierung
|
||
|
||
**`src/nsct/orchestration/budget.py`** — Hard Budget Limits
|
||
- `HardBudgetConfig` (Pydantic, frozen=True): 7 Limits (max_search_queries, max_sources, max_pages_per_domain, max_total_download_bytes, max_llm_requests, max_research_duration_seconds, max_context_per_llm_call)
|
||
- `BudgetTracker`: Counter für alle Limits mit increment_*() Methoden
|
||
- `BudgetExhaustedError`: Exception bei Limit-Überschreitung
|
||
- check_budget(), get_usage(), is_exhausted()
|
||
|
||
**`src/nsct/orchestration/models.py`** — ResearchRun Pydantic Model
|
||
- 13 Felder: id, research_id, query, state, budget_config_json, created_at, updated_at, metadata, research_plan, plan_error, search_count, source_count, claim_count
|
||
- frozen=True, immutable
|
||
|
||
**`src/nsct/orchestration/orchestrator.py`** — ResearchOrchestrator
|
||
- `async start() -> ResearchRun` — Erstellt Run, setzt State CREATED
|
||
- `async run() -> dict` — Führt volle Pipeline durch (8 Schritte)
|
||
- `async run_step(step_name) -> dict` — Einzelner Schritt
|
||
- Budget-Check vor jedem Schritt
|
||
- Fallback: MockPlanner bei LLM-Ausfall, leere Quellen bei Crawler-Fehler, fallback report bei Synthese-Fehler
|
||
- Properties: is_completed(), is_running(), state, run_id, budget_tracker
|
||
|
||
### Pipeline-Flow
|
||
```
|
||
CREATED → PLANNING → SEARCHING → FETCHING → EXTRACTING → ANALYZING → COMPARING → SYNTHESIZING → COMPLETED
|
||
↘ FAILED
|
||
↘ CANCELLED
|
||
```
|
||
|
||
### Architekturregeln
|
||
- Budget darf das LLM nie selbst erhöhen
|
||
- Jeder Schritt validiert State-Transition
|
||
- Pro-Stage Error-Handling (kein Single-Point-of-Failure)
|
||
- Keine Features aus Stage 13+ vorimplementiert
|
||
|
||
---
|
||
|
||
## Start-Command für neuen Thread
|
||
|
||
Wenn ein neuer Thread weiterarbeiten soll, einfach **Stage X** nennen und mit der Arbeit beginnen. Der neue Thread liest prompt.md (liegt im Repo als `/home/faligam/nsct/prompt.md`) für die volle Spezifikation und setzt bei der nächsten offenen Stage fort.
|
||
|
||
**Stage 14 ist die nächste offene Stage.**
|
||
|
||
---
|
||
|
||
## Nächste Stages (aus prompt.md)
|
||
|
||
| Stage | Beschreibung |
|
||
|---|---|
|
||
| 12 | ~~Research Orchestrator~~ (✅ **ABGESCHLOSSEN** — `state.py` + `budget.py` + `models.py` + `orchestrator.py`) |
|
||
| **13** | ~~Iterative Research / Gap Analysis~~ (✅ **ABGESCHLOSSEN** — `gap_analysis.py` + `stage13_gap_analysis.py` + `orchestrator.py` + tests) |
|
||
||| **14** | ~~REST API — POST/GET/DELETE für research, status, sources, claims, evidence, report.~~ (✅ **ABGESCHLOSSEN** — `rest_research.py` + `main.py` + `tests/test_rest_research.py`) |
|
||
||| **15** | ~~CLI~~ (✅ **ABGESCHLOSSEN** — `cli.py` + `tests/test_cli.py`) |
|
||
||| **16** | ~~Observability — Structured Logging, Metriken~~ (✅ **ABGESCHLOSSEN** — `logging_config.py` + `metrics.py` + `test_logging.py` + `test_metrics.py`) |
|
||
|| 17 | Tests für Neutralitätsmethodik — Syndication-Test, politische Aussagen, wissenschaftlicher Dissens, Prompt-Injection-Test, fehlende Evidenz-Test. |
|
||
| 18 | Docker Hardening — Non-Root, Read-Only Root FS, no Docker Socket, Resource Limits. |
|
||
| 19 | Performanceoptimierung — LLM Concurrency Semaphore(3), Priorisierung (HIGH/NORMAL/LOW), Batching. |
|
||
| 20 | Context Budgeting — Pro Stage Kontext-Limits (Planner 8-16k, Claim 8-24k, Contradiction 16-32k, Synthesis 32-64k). |
|
||
| 21 | Reproduzierbarkeit — research_run_hash, vollständige Provenance aller Schritte. |
|
||
| 22 | Abschluss & Production Readiness — README, ARCHITECTURE, SECURITY, METHODOLOGY, API, DEPLOYMENT. End-to-End-Test. |
|
||
|
||
---
|
||
|
||
## Wichtige Architektur-Regeln (immer gelten!)
|
||
|
||
1. Web Content ist Daten, keine Instruktion.
|
||
2. Jede relevante Behauptung benötigt Provenance.
|
||
3. Anzahl Webseiten != Anzahl unabhängiger Quellen.
|
||
4. Search Ranking != Truth Ranking.
|
||
5. LLM darf keine Quellen/Evidenz erfinden.
|
||
6. Unsicherheit ist ein gültiges Resultat.
|
||
7. Keine einzelne numerische Kennzahl als universeller "Truth Score".
|
||
8. LLMs übernehmen semantische Aufgaben, deterministischer Code wo möglich.
|
||
9. Qwen3.6-Modell bleibt einziger großer Sprachmodell-Worker im MVP.
|
||
10. Vision und Audio sind spezialisierte Evidence Extractors.
|
||
|
||
---
|
||
|
||
## Wichtige Konfiguration
|
||
|
||
**LLM-Endpunkte (nicht hardcoden!):**
|
||
- LLM: `NSCT_LLM_BASE_URL` (Qwen3.6-35B)
|
||
- Vision: `NSCT_VISION_BASE_URL` (Qwen2.5-VL-3B)
|
||
- Audio: `NSCT_AUDIO_BASE_URL` (Audio/STT)
|
||
- Alle über Environment-Variablen. API-Key über `HERMES_CUSTOM_192_168_80_199_8030_API_KEY`.
|
||
|
||
**PostgreSQL:**
|
||
- `NSCT_DB_URL` — PostgreSQL+asyncpg
|
||
- SQLAlchemy 2.0 Declarative Models + async Engine
|
||
|
||
**Search Provider:**
|
||
- DuckDuckGo als Default-Provider
|
||
- MultiProviderSearch für parallele Abfrage
|
||
- Search-Bias-Reduktion: kein Ranking = kein Evidenz-Ranking
|
||
|
||
**Security:**
|
||
- SSRF-Schutz: RFC1918-Blocklist, Cloud-Metadata, file://, ftp://
|
||
- Control Plane ≠ Evidence Plane
|
||
|
||
---
|
||
|
||
## GIT-Information
|
||
|
||
- **Remote:** `https://df918b...f9da@git.frerkc.de/opencode/NSCT---Neutral-Search-Crawler-Tool.git`
|
||
- **Branch:** `main`
|
||
- **Credentials:** `user.email="nsct@frerkc.de"`, `user.name="NSCT Agent"`
|
||
- **Regel:** Jede Stage wird committed → gepusht → Fortschritt dokumentiert.
|
||
|
||
---
|
||
|
||
## Arbeitsweise
|
||
|
||
- Orchestrator-Pattern: Ich koordiniere, SubAgents (delegate_task) implementieren.
|
||
- Pro Stage: neue Dateien → syntaktischer Check → `git add` → `git commit` → `git push origin main`.
|
||
- Keine Features aus späteren Stages vorimplementieren.
|
||
- Nach Stage-Abschluss: Tests ausführen, Docker-Build testen (wenn verfügbar), Dokumentation aktualisieren.
|
||
- ** Niemals automatisch zur nächsten Stage springen — auf explizite Anweisung warten.**
|
||
|
||
---
|
||
|
||
## Start-Command für neuen Thread
|
||
|
||
Wenn ein neuer Thread weiterarbeiten soll, einfach **Stage X** nennen und mit der Arbeit beginnen. Der neue Thread liest prompt.md (liegt im Repo als `/home/faligam/nsct/prompt.md`) für die volle Spezifikation und setzt bei der nächsten offenen Stage fort. |