Implement Phase 3 Agentic Edge Validation and Chunk-Aware Multigraph-System
All checks were successful
Deploy mindnet to llm-node / deploy (push) Successful in 4s

- Introduced final validation gate for edges with candidate: prefix.
- Enabled automatic generation of mirror edges for explicit connections.
- Added support for Note-Scope zones to facilitate global connections.
- Enhanced section-based links in the multigraph system for improved edge handling.
- Updated documentation and added new ENV variables for configuration.
- Ensured no breaking changes for end users, maintaining full backward compatibility.
This commit is contained in:
Lars 2026-01-14 22:26:12 +01:00
parent 273c4c6919
commit 39a6998123
4 changed files with 608 additions and 0 deletions

1
debug.log Normal file
View File

@ -0,0 +1 @@
[0114/152756.633:ERROR:third_party\crashpad\crashpad\util\win\registration_protocol_win.cc:108] CreateFile: Das System kann die angegebene Datei nicht finden. (0x2)

View File

@ -0,0 +1,221 @@
<!-- FILE: konzept_zielbild_kausales_retrieval_mindnet.md -->
---
id: konzept_zielbild_kausales_retrieval_mindnet
title: Konzept & Zielbild Kausalketten-Prüfung und kausales Retrieval für Mindnet (Qdrant)
type: concept
status: draft
created: 2026-01-13
lang: de
tags:
- mindnet
- obsidian
- knowledge_graph
- causal_chains
- retrieval
---
# Konzept & Zielbild Kausalketten-Prüfung und kausales Retrieval für Mindnet (Qdrant)
## Ziel
Mindnet soll zu beliebigen Fragestellungen **die richtigen Notizen** nicht nur über semantische Nähe (Embeddings), sondern über **kausale Relevanz** finden.
Parallel soll ein Authoring-Assistent helfen, Obsidian-Notizen so anzulegen, dass Kausalketten **formal konsistent** und **traversierbar** sind.
---
## Ausgangslage / Problem
- Der Wissensgraph wird in Qdrant gepflegt; aktuelles Retrieval basiert primär auf **Gewichtung + semantischer Nähe**.
- Ergebnis: thematisch nahe Treffer, aber oft **nicht antwortrelevant** (fehlende Ursachen-/Folgenbezüge).
- Obsidian-Notizen enthalten Edges (Vorwärts/Rückwärts); Qualität hängt von:
- korrekter Relation (Kausalität vs Chronologie),
- konsistenten Node-Namen,
- Inversen (gegenläufigen Beziehungen),
- sauberer Typisierung ab.
---
## Grundannahmen
- Viele Antworten benötigen einen **Erklärungspfad** statt eines Einzel-Treffers:
- Ursache → Mechanismus/Transformation → Entscheidung → Wirkung → Rückkopplung
- Kausalität ist im Graph als gerichtete Kanten modelliert und über inverse Typen **bidirektional navigierbar**:
- `resulted_in``caused_by`
- `followed_by``preceeded_by`
- `derived_from``source_of`
- `impacts``impacted_by`
---
## System-Zielbild (2 Hauptkomponenten)
### 1) Authoring-Assistent (Obsidian Graph Linter + Chain Explorer)
Zweck: Qualitätssicherung beim Erstellen/Ändern von Notizen.
**Kernfunktionen**
- **Formale Prüfungen**
- Canonical Edge vs Alias (Normalisierung nach `edge_vocabulary`)
- Zielnoten existieren / leere Links als `open_question` oder TODO markieren
- Tippfehler/Node-Splitting erkennen (mehrere Schreibweisen desselben Knoten)
- Edge-Typ zulässig für Note-Typ (z.B. keine Kausal-Edges aus `open_question`)
- **Semantische Plausibilität (regelbasiert)**
- Chronologie (`followed_by`) ≠ Kausalität (`resulted_in`)
- Hub-/Index-Noten nutzen primär `related_to/consists_of` statt Kausalität
- Prinzipien bevorzugt `derived_from/based_on` statt pauschal `caused_by`
- **Ketten-Integrität**
- „Gap“-Warnungen (Sprünge ohne Zwischennoten)
- Zyklen ohne Sinn (A caused_by B und B caused_by A)
- Mehrfachursachen transparent markieren
**Outputs**
- Lint-Report pro Note (Fehler/Warnung/Empfehlung)
- Chain-Preview (24 Schritte vorwärts/rückwärts)
- Optional: Auto-Fix-Vorschläge (Alias→Canonical, Link-Normalisierung, Inversen ergänzen)
---
### 2) Mindnet Retrieval: Hybrid aus Embeddings + Graph Traversal + Reranking
Zweck: Aus einer Frage automatisch eine **kleine, kausal zusammenhängende** Menge von Notizen auswählen.
**Pipeline**
1. **Seed Retrieval (Qdrant Embeddings)**
- Top-K Kandidaten (z.B. 30) als Startpunkte
- Optional: Filter nach Node-Typ (z.B. bei „Welche Entscheidungen…“)
2. **Intent-Klassifikation (Frage → Richtung & Kettenform)**
- Regelbasiert (Start) oder später ML-Classifier
- Output: `{direction, preferred_edges, target_types, max_hops, need_explanation_chain}`
3. **Graph Expansion (Multi-Source Multi-Hop Traversal)**
- Expandiert von Seeds 13 Hops (typisch 24)
- Richtungslogik:
- „Warum/Ursache“ → rückwärts (`caused_by`, `preceeded_by`, `derived_from`)
- „Folgen/Ergebnis“ → vorwärts (`resulted_in`, `followed_by`, `impacts`)
- „Entwicklung/Veränderung“ → beides (forward + backward)
- Ergebnis: Pfad-Kandidaten (nicht nur Nodes)
4. **Reranking (Antwortrelevanz)**
- Score = Semantik + Pfadqualität + Antwortform-Passung
5. **Antwort-Bausteine (Minimal Explanation Subgraph)**
- Merged Top-Pfade zu einem kleinen Subgraph (z.B. 812 Nodes)
- Pruning nach zentralen Knoten und erklärender Kettenform
---
## Spezifikation: Intent → Traversal Mode (Heuristik)
### Intent-Struktur
- `direction`: `backward | forward | both`
- `preferred_edges`: Menge Edge-Typen
- `target_types`: Menge Node-Typen
- `max_hops`: int
- `need_explanation_chain`: bool
### Heuristik (Deutsch)
- **Warum / Ursache / Auslöser / wodurch / wie kam es dazu**
- direction: backward
- preferred_edges: `{caused_by, preceeded_by, derived_from}`
- target_types: `{experience, decision, strategy, state}`
- max_hops: 24
- **Was führte zu / Folgen / Auswirkungen / resultierte in**
- direction: forward
- preferred_edges: `{resulted_in, followed_by, impacts}`
- target_types: `{decision, strategy, state, principle}`
- max_hops: 24
- **Entwicklung / Veränderung / Weltbild / Glaubenssatz / Charakter**
- direction: both
- preferred_edges backward: `{caused_by, derived_from}`
- preferred_edges forward: `{resulted_in, impacts}`
- target_types: `{principle, state, strategy, decision}`
- max_hops: 24
- need_explanation_chain: true
---
## Spezifikation: Traversal (Weighted Multi-Hop)
### Gewichte (Startwerte)
**Edge Weights**
- `resulted_in`: 1.00
- `caused_by`: 1.00
- `derived_from`: 0.90
- `source_of`: 0.90
- `impacts`: 0.70
- `impacted_by`: 0.70
- `followed_by`: 0.50
- `preceeded_by`: 0.50
- `related_to`: 0.25
- `part_of/consists_of`: 0.25
**Node-Type Weights**
- `experience`: 1.00
- `decision`: 1.00
- `strategy`: 0.90
- `state`: 0.85
- `principle`: 0.85
- `insight(hub)`: 0.35
- `open_question/hypothesis/white_spot`: 0.00 (Filter)
**Hop Decay**
- `hop_decay(h) = 0.75^h`
### Traversal-Logik (pseudocode-nah)
- Multi-Source-Expansion ab Seeds
- Pfade priorisiert nach kumuliertem Pfadscore
- `visited` verhindert endlose Wiederholungen
---
## Spezifikation: Reranking (Semantik + Kausalität + Antwortform)
### Final Score
- `final_score(path) = alpha*semantic + beta*coherence + gamma*shape_match`
Startwerte:
- `alpha = 0.55` (Semantik)
- `beta = 0.30` (Kausal-Kohärenz)
- `gamma = 0.15` (Passung zur Frageform)
**Causal Coherence**
- Bonus, wenn Pfad Kausal-Edges enthält (`resulted_in/caused_by/derived_from`)
- Malus, wenn nur Navigation/Chronologie enthalten ist
- Bonus für Kernform: `experience → decision → (state|strategy|principle)`
---
## Output: Minimal Explanation Subgraph (MES)
Ziel: nicht eine Liste, sondern ein erklärendes Subgraph-Set.
**Regeln**
- Top-Pfade (z.B. 35) mergen
- max_nodes: 812
- Pruning:
- Hubs raus, wenn sie nur Navigation sind
- Decision/Principle/State bevorzugen (Antwortanker)
- Bridge-Nodes behalten (in mehreren Pfaden vorkommend)
---
## Authoring-Regeln (Graph-Hygiene) harte Leitplanken
1. Kausalität nur auf atomaren Noten (`experience/decision/state/strategy/principle`)
2. Hubs/Indexnoten: primär `related_to/consists_of` (keine „Hub verursacht X“-Kausalität)
3. Inverse Edges müssen erzeugbar sein (oder Build-Step erzeugt sie deterministisch)
4. Chronologie strikt trennen (`followed_by` ≠ `resulted_in`)
5. Prinzipien: `derived_from/based_on` für Herkunft (statt pauschal `caused_by`)
6. Leere Links als `open_question` oder TODO ohne Kausal-Edge
7. Kanonische Dateinamen: Node-Splitting verhindern
---
## Nutzen / Erfolgskriterien
- **Bessere Answer Relevance**: Mindnet liefert Knoten mit erklärender Kausalstruktur statt nur thematischer Nähe
- **Erklärbarkeit**: Antwort kann mit Pfad(en) begründet werden
- **Debuggability**: Fehlantworten lassen sich auf falsche/fehlende Kanten zurückführen
- **Authoring-Effizienz**: Assistent verhindert typische Edge-Fehler früh
---
## Offene Punkte (für nächste Iteration)
- Intent-Taxonomie (812 Frageklassen) finalisieren und evaluieren
- Welche Edges werden als „kausal“ im engeren Sinne akzeptiert?
- Welche Node-Typen sind Pflichtmetadaten für Mindnet?
- Evaluation: Retrieval-Qualität mit/ohne Traversal (A/B)

View File

@ -0,0 +1,250 @@
<!-- DOCUMENT 1: pflichtenheft_obsidian_plugin_mindnet_assistant.md -->
---
id: pflichtenheft_obsidian_plugin_mindnet_assistant
title: Pflichtenheft Obsidian Plugin „Mindnet Causal Assistant“
type: specification
status: draft
created: 2026-01-13
lang: de
---
# Pflichtenheft Obsidian Plugin „Mindnet Causal Assistant“
## 1. Zielsetzung
Das Plugin unterstützt den Nutzer beim Erstellen und Pflegen eines narrativ-kausalen Wissensgraphen in Obsidian (Mindnet).
Es bietet:
- **Aktive Authoring-Unterstützung** (Guided Note Creation / Interview Flow)
- **Kausalketten-Prüfung** (Chain Explorer, Vorwärts/Rückwärts)
- **Linting + Auto-Fixes** (Graph-Hygiene, konsistente Kanten, Namensnormalisierung)
- **Export/Integration** der strukturierten Graph-Daten für ein Retrieval-System (Qdrant + Graph-Index)
## 2. Kontext & Randbedingungen
- Obsidian Vault enthält Notes als Markdown, jede Entität eine Datei.
- Notes enthalten Frontmatter (`id,title,type,status,...`) und Edges in Callout-Blöcken.
- Edge-Vokabular inklusive Aliasse & Inversen ist verfügbar (z.B. `edge_vocabulary.md`).
- Der Graph soll später von Mindnet traversierbar sein (Vorwärts/Rückwärts über inverse Relationen).
- Plugin muss offline nutzbar sein; optionale Backend/LLM-Integration ist konfigurierbar.
## 3. Begriffsdefinitionen
- **Node**: eine Obsidian Markdown-Datei (Entität).
- **Edge**: gerichtete Beziehung zwischen zwei Nodes (canonical edge type).
- **Alias**: alternative Edge-Bezeichnung in Notes, die auf canonical mapped wird.
- **Inverse**: Gegenkante zu einer Edge, laut Vokabular (z.B. `resulted_in``caused_by`).
- **Hub/Index**: Note, die primär navigiert (typisch `type: insight`), keine Kausalursache.
## 4. Scope
### In Scope (MVP → V2)
**MVP**
- Parser für Frontmatter + Edge-Callouts
- Normalizer: Alias → Canonical; optional Inversen-Erkennung
- Linter: Regelset (Error/Warn/Info) + Report
- Chain Explorer: forward/backward traversal (14 hops) ab aktueller Note
- Quickfixes: Edge-Typ ersetzen, Links normalisieren, Missing Note Stub erzeugen
**V2**
- Guided Authoring (Interview Flow) für `experience/decision/principle/state/strategy`
- Refactor Mode: Text → Node/Edge-Kandidaten + Review UI
- Export/Sync: JSON Graph Export + optional Qdrant Sync (separater Service)
### Out of Scope (initial)
- Vollautomatische Kausalitäts-Interpretation ohne User-Bestätigung
- Vollständige UI-Graph-Visualisierung (Obsidian Graph View bleibt nutzbar)
- Direkte medizinische/psychologische Beratung
## 5. Nutzerrollen & Use Cases
### Rolle: Nutzer (Author)
- UC1: „Ich schreibe eine Note und will Kanten prüfen“
- UC2: „Ich will von einem Ereignis aus die Kausalkette sehen“
- UC3: „Ich will eine neue Experience/Decision Note sauber anlegen“
- UC4: „Ich habe Text und will daraus Kandidaten extrahieren“
- UC5: „Ich will leere Links als open_question sauber erzeugen“
### Rolle: System/Indexer (Mindnet)
- UC6: „Ich brauche exportierbare adjacency lists + canonical edges“
## 6. Funktionale Anforderungen (FR)
### FR1: Vault Parsing
- FR1.1 Parse Frontmatter (YAML): `id,title,type,status,date,tags,...`
- FR1.2 Parse Edge-Callouts im Format:
- `> [!abstract]- 🕸️ Semantic Mapping`
- `>> [!edge] <relation>`
- `>> [[target]]`
- FR1.3 Extrahiere alle WikiLinks `[[...]]` aus Edge-Blocks
- FR1.4 Erkenne Datei-Pfade, Dateinamen und canonical node identifiers (Dateiname ohne `.md`)
**Output (intern)**
```ts
type Node = { id?: string; title?: string; type?: string; status?: string; path: string; slug: string };
type Edge = { srcSlug: string; dstSlug: string; rawType: string; canonicalType?: string; line?: number; blockId?: string };
```
### FR2: Edge Normalization
- FR2.1 Map rawType/Alias auf canonical edge type via Edge Vocabulary
- FR2.2 Speichere Mapping-Entscheidungen (raw → canonical) pro Edge
- FR2.3 Liefere inverse edge type (`inverseType`) pro canonical edge type (sofern definiert)
### FR3: Linting
- FR3.1 Führe Checkliste von Regeln aus (siehe separates Dokument)
- FR3.2 Liefere LintReport mit Severity (ERROR/WARN/INFO), Location (file, line), Fix-Vorschlägen
- FR3.3 Quickfix: wende Fix auf Note an (Text edit), mit Preview/Diff
### FR4: Chain Explorer (Traversal)
- FR4.1 Startpunkt: aktuelle Note im Editor
- FR4.2 Forward traversal: `resulted_in`, `followed_by`, `impacts`, `source_of`, optional `related_to`
- FR4.3 Backward traversal: `caused_by`, `preceeded_by`, `derived_from`, `impacted_by`
- FR4.4 Konfigurierbare maxHops (Default 3)
- FR4.5 Ergebnis als Liste von Pfaden + kompaktes Subgraph-Summary (Nodes/Edges)
### FR5: Missing Notes / Stubs
- FR5.1 Erkenne, wenn Edge-Target nicht existiert
- FR5.2 Biete „Create Stub Note“ an:
- Template basierend auf Typ (default `open_question` wenn unbekannt)
- Einhaltung Naming-Rules: `a-z0-9_`
- FR5.3 Optional: convert TODO-Link → open_question note
### FR6: Guided Authoring (V2)
- FR6.1 Wizard für neue Notes: Auswahl Typ → Fragen (eine nach der anderen)
- FR6.2 Wizard erstellt Datei mit Template + initialen Edge-Blocks
- FR6.3 Jede automatische Edge-Vermutung ist „review-required“
### FR7: Refactor Mode (V2)
- FR7.1 Extrahiere aus aktuellem Note-Text Kandidaten:
- Event-Kandidaten (Datum/Ort/Verben)
- Decision-Kandidaten („entschied“, „nahm an“, „wechselte“)
- Principle-Kandidaten („ich glaube“, „ich habe gelernt“)
- Relation-Kandidaten („dadurch“, „führte zu“, „weil“)
- FR7.2 UI-Review: Checkbox-Liste zum Erstellen/Verwerfen
- FR7.3 Generiere Notes + Edges nur nach Bestätigung
### FR8: Export (MVP optional / V2 empfohlen)
- FR8.1 Export JSON: Nodes + canonical edges + inverses
- FR8.2 Export adjacency list pro node slug
- FR8.3 Optional: webhook/CLI hook für Indexer (Qdrant)
## 7. Nicht-funktionale Anforderungen (NFR)
- NFR1: Performant bei 10k Notes (incremental parse, caching)
- NFR2: Offline-first; LLM/Backend optional
- NFR3: Deterministische Normalisierung (gleiches Input → gleiches Output)
- NFR4: Kein Erfinden von Fakten: Auto-Edge nur als Vorschlag
- NFR5: Sicheres Editieren (Diff/Undo via Obsidian APIs)
- NFR6: Konfigurierbarkeit (YAML/Settings Tab): maxHops, allowed edges, strict mode
## 8. Technisches Lösungsdesign
### 8.1 Obsidian Plugin Struktur (TypeScript)
- `main.ts` Plugin lifecycle, commands, views
- `settings.ts` Einstellungen
- `parser/` Markdown + callout parser
- `graph/` Node/Edge model, normalization, traversal
- `lint/` Rules engine, reports, quickfixes
- `ui/` Sidebar view, modals, diff preview
### 8.2 Speicherung / Cache
- In-memory cache: map `path → parsed Node + edges + hash`
- Incremental update: on file change events re-parse only changed file
- Optional persisted cache in `.obsidian/plugins/.../cache.json`
### 8.3 Edge Vocabulary Integration
- Input: `edge_vocabulary.md` im Vault ODER eingebettete JSON Ressource
- Parsing:
- canonical edge types
- alias list
- inverse mapping
- Fallback: minimal builtin vocabulary, wenn Datei fehlt
### 8.4 Traversal Engine
- Graph Index: adjacency lists aus canonical edges
- Traversal:
- BFS mit hop limit
- optional weighted expansion (für Chain Explorer „relevant paths first“)
### 8.5 Quickfix Engine
- Applies patches auf Markdown:
- Replace edge type token im Callout (`>> [!edge] ...`)
- Rename link targets (replace `[[old]]``[[new]]`)
- Insert stub note file from template
- Safety:
- Show diff modal
- Use Obsidian editor transactions / file API
### 8.6 Optional Backend / LLM (V2)
- Backend (local node service) für:
- text extraction (Refactor Mode)
- suggestion generation
- Communication:
- HTTP local (`127.0.0.1`) oder WebSocket
- API key storage via Obsidian settings (encrypted if possible)
- Claude-code/Cursor: nutzt Code-Agent für Implementierung, nicht zur Runtime.
## 9. UI/UX Anforderungen
### 9.1 Sidebar View „Mindnet Assistant“
Tabs:
- **Validate**: Lint Report + Fix Buttons
- **Chains**: Forward/Backward Chain Explorer + Copy as text
- **Create** (V2): Wizard new note
- **Refactor** (V2): Extract candidates
### 9.2 Commands (Command Palette)
- `Mindnet: Validate current note`
- `Mindnet: Validate vault (selected folders)`
- `Mindnet: Show chains from current note`
- `Mindnet: Normalize edges in current note`
- `Mindnet: Create stub for missing links`
- (V2) `Mindnet: Start guided authoring`
- (V2) `Mindnet: Refactor current note to graph`
## 10. Akzeptanzkriterien
- AK1: Plugin erkennt Edge-Callouts und normalisiert Aliasse deterministisch
- AK2: Linter findet Node-Splitting (mindestens Levenshtein/ähnliche Slugs) und Missing Notes
- AK3: Chain Explorer liefert identische Pfade vorwärts/rückwärts bei inversen Edge-Paaren
- AK4: Quickfix ersetzt Edge-Typen ohne Markdown zu zerstören; Undo funktioniert
- AK5: Export JSON enthält canonical edges + inverse types
## 11. Deliverables
- Obsidian Plugin (TS) mit MVP Features
- Dokumentation:
- Install/Build
- Settings
- Rule reference
- Example vault sample
- Optional: JSON Export Format Spec (nodes/edges)
---
## 12. Prompts für Code-Agenten (Cursor / Claude-code)
### Prompt A (Repo Scaffold + MVP)
> Du bist ein Senior TypeScript Engineer. Implementiere ein Obsidian Plugin „Mindnet Causal Assistant“.
> Ziele MVP:
> 1) Parse Frontmatter (YAML) und Edge-Callouts im Format:
> `> [!abstract]- 🕸️ Semantic Mapping``>> [!edge] <relation>``>> [[target]]`.
> 2) Normalisiere Edge Aliasse auf canonical edge types (Vokabular als JSON im Code; später ersetzbar).
> 3) Baue eine Sidebar View mit Tabs „Validate“ und „Chains“.
> 4) Implementiere Lint Regeln: missing target note, alias-not-normalized, hub-has-causal-edge, chronology-vs-causality warning.
> 5) Implementiere Chain Explorer (forward/backward, maxHops=3).
> 6) Implementiere Quickfix: replace edge type token, create stub note.
> Nutze Obsidian APIs, schreibe sauberen TS Code, mit Tests für Parser/Normalizer.
### Prompt B (Parser Unit Tests)
> Schreibe Unit Tests für den Markdown Parser:
> - erkennt mehrere Edge-Blocks pro Datei
> - erkennt mehrere Targets pro Edge
> - liefert line numbers
> - ignoriert WikiLinks außerhalb der Semantic Mapping Callouts
> Nutze vitest/jest. Erzeuge fixtures.
### Prompt C (Lint Engine + Quickfix)
> Implementiere eine Lint Engine als Rule-Pipeline.
> Jede Regel: id, severity, detect(node, graph) -> findings, fix(finding)->patch.
> Baue eine Diff Preview Modal und applyPatch über Obsidian file API.
> Implementiere zunächst 6 Regeln aus der Checkliste.
### Prompt D (Vocabulary Loader)
> Implementiere einen VocabularyLoader:
> - lädt entweder eingebettetes JSON oder eine Vault-Datei `edge_vocabulary.md`
> - parst canonical types, aliases, inverse
> - bietet getCanonical(raw) und getInverse(canonical)
> Fallback auf builtin vocabulary wenn parsing fehlschlägt.

View File

@ -0,0 +1,136 @@
<!-- DOCUMENT 2: checklist_lint_regeln_mindnet_assistant.md -->
---
id: checklist_lint_regeln_mindnet_assistant
title: Checkliste Lint-Regeln für Mindnet Causal Assistant
type: specification
status: draft
created: 2026-01-13
lang: de
---
# Checkliste Lint-Regeln für Mindnet Causal Assistant
## Severity Levels
- **ERROR**: bricht Traversal/Indexer oder erzeugt falsche Nodes
- **WARN**: wahrscheinlich falsche Semantik / schlechter Retrieval-Impact
- **INFO**: Optimierung / Empfehlung
---
## A. Graph-Integrität & Naming
### L1 (ERROR) Missing Target Note
**Wenn:** Edge target `[[X]]` existiert nicht als Datei im Vault
**Dann:** Finding `missing_target`
**Fix:** „Create Stub Note“ (default `type: open_question`) oder remove edge
### L2 (ERROR) Node Splitting durch Schreibvarianten
**Wenn:** mehrere Targets im Vault sind ähnlich (slug distance), oder in Edges mehrere Varianten vorkommen
**Dann:** Finding `node_split_candidate`
**Fix:** Vorschlag canonical slug + bulk replace links
### L3 (ERROR) Invalid Filename Policy
**Wenn:** Dateiname enthält Zeichen außerhalb `[a-z0-9_]`
**Dann:** Finding `invalid_filename`
**Fix:** Rename file + update all backlinks
---
## B. Edge-Formale Regeln
### L4 (ERROR) Unknown Edge Type / Unmapped Alias
**Wenn:** raw edge type nicht im Vokabular (alias→canonical)
**Dann:** Finding `unknown_edge_type`
**Fix:** Edge type ersetzen durch best guess oder user selection
### L5 (WARN) Alias not normalized
**Wenn:** raw edge type ist Alias, canonical bekannt, aber Note enthält Alias
**Dann:** Finding `alias_not_normalized`
**Fix:** Replace raw with canonical (optional config)
### L6 (WARN) Missing Inverse Edge (optional strict mode)
**Wenn:** Edge A->B existiert, inverse nach Vokabular fehlt in B
**Dann:** Finding `missing_inverse`
**Fix:** Add inverse edge to target note (review + diff)
---
## C. Semantik: Kausalität vs Chronologie
### L7 (WARN) Chronology used as Causality
**Wenn:** Knoten/Target wirkt wie Prozessschritt („warten“, „gehen“, „ankommen“) und Edge type ist `resulted_in`
**Dann:** Finding `chronology_as_causality`
**Fix:** Vorschlag `followed_by` (inverse `preceeded_by`)
### L8 (INFO) Kausalität ohne Brücken (Gap)
**Wenn:** Pfad springt von Ereignis direkt zu Entscheidung, aber intermediäre Knoten fehlen (heuristisch)
**Dann:** Finding `missing_bridge_node`
**Fix:** Vorschlag „Create open_question bridge“ (z.B. „Was war der konkrete Auslöser…?“)
---
## D. Node-Type Regeln
### L9 (ERROR) Causal edges from open_question/hypothesis/white_spot
**Wenn:** node.type in `{open_question, hypothesis, white_spot}` und Edge type in `{caused_by, resulted_in, impacts, derived_from}`
**Dann:** Finding `invalid_causal_edge_from_uncertain`
**Fix:** Replace with `related_to` oder remove edge
### L10 (WARN) Hub/Insight Note trägt Kausalität
**Wenn:** node.type == `insight` (oder Hub-Pattern) und hat `caused_by/resulted_in`
**Dann:** Finding `hub_has_causality`
**Fix:** Replace edges with `related_to` und verschiebe Kausalität in atomare Notes
### L11 (WARN) Principle uses caused_by for origin
**Wenn:** node.type == `principle` und enthält `caused_by` zu Erlebnissen
**Dann:** Finding `principle_origin_edge`
**Fix:** Vorschlag `derived_from` oder `based_on`
### L12 (INFO) Decision without caused_by
**Wenn:** node.type == `decision` und hat keine `caused_by`-Kanten
**Dann:** Finding `decision_without_causes`
**Fix:** Wizard: „Was war der Auslöser?“ → create open_question or add edges
---
## E. Redundanz & Zyklen
### L13 (WARN) Duplicate Edges
**Wenn:** identische canonical edge mehrfach gesetzt (src,type,dst)
**Dann:** Finding `duplicate_edge`
**Fix:** remove duplicates
### L14 (WARN) Cycles in pure causality subgraph
**Wenn:** Zyklus ausschließlich über `{caused_by,resulted_in,derived_from,source_of}`
**Dann:** Finding `causal_cycle`
**Fix:** Markiere zur Review; oft ist eine Kante falsch gerichtet
---
## F. Traversal-Optimierung (Retrieval-Wirkung)
### L15 (INFO) Overuse of related_to
**Wenn:** Note enthält nur `related_to` und keine spezifischeren Kanten
**Dann:** Finding `weak_semantics`
**Fix:** Vorschlag: präzisere Beziehungstypen setzen
### L16 (INFO) Missing type metadata
**Wenn:** Frontmatter `type` fehlt
**Dann:** Finding `missing_type`
**Fix:** Prompt user to choose type; set via template
### L17 (INFO) Missing date on experience
**Wenn:** node.type == `experience` und kein Datum/Zeitraum vorhanden
**Dann:** Finding `missing_date_experience`
**Fix:** Prompt: „Wann ungefähr?“ → set `date` oder `time_range`
---
## Suggested Implementation Notes
- Jede Regel liefert:
- `ruleId`, `severity`, `message`, `location`, `evidence`, `quickFixes[]`
- QuickFixes sind Patch-Operationen:
- replaceText(range, text)
- insertBlock(atLine, block)
- createFile(path, content)
- renameFile(old, new) + updateLinks(glob)