This commit is contained in:
parent
8d3bc1c2e2
commit
18b90c8df3
|
|
@ -20,6 +20,7 @@ class GraphExplorerService:
|
|||
self.chunks_col = f"{prefix}_chunks"
|
||||
self.edges_col = f"{prefix}_edges"
|
||||
self._note_cache = {} # Cache für Note-Payloads
|
||||
self._ref_resolution_cache = {} # Cache für aufgelöste Referenzen (ref_str -> note_payload)
|
||||
self._note_cache = {}
|
||||
|
||||
def get_note_with_full_content(self, note_id):
|
||||
|
|
@ -457,6 +458,11 @@ class GraphExplorerService:
|
|||
"""
|
||||
if not ref_str: return None
|
||||
|
||||
# Cache-Check: Wenn wir diese Referenz bereits aufgelöst haben, verwende das Ergebnis
|
||||
if ref_str in self._ref_resolution_cache:
|
||||
cached_result = self._ref_resolution_cache[ref_str]
|
||||
return cached_result
|
||||
|
||||
# Fall A: Enthält # (kann Chunk-ID oder Wikilink mit Abschnitt sein)
|
||||
if "#" in ref_str:
|
||||
try:
|
||||
|
|
@ -466,7 +472,9 @@ class GraphExplorerService:
|
|||
note_id = res[0].payload.get("note_id")
|
||||
if note_id:
|
||||
note = self._fetch_note_cached(note_id)
|
||||
if note: return note
|
||||
if note:
|
||||
self._ref_resolution_cache[ref_str] = note
|
||||
return note
|
||||
except Exception:
|
||||
pass
|
||||
|
||||
|
|
@ -474,7 +482,9 @@ class GraphExplorerService:
|
|||
# z.B. "20250101-meine-note#Abschnitt" -> "20250101-meine-note"
|
||||
possible_note_id = ref_str.split("#")[0]
|
||||
note = self._fetch_note_cached(possible_note_id)
|
||||
if note: return note
|
||||
if note:
|
||||
self._ref_resolution_cache[ref_str] = note
|
||||
return note
|
||||
|
||||
# Versuch 3: Wikilink-Text mit Abschnitt (z.B. "Meine Prinzipien 2025#P3 – Disziplin")
|
||||
# WICHTIG: target_id ist der vollständige Wikilink-Text, wir müssen den Titel-Teil extrahieren
|
||||
|
|
@ -529,26 +539,62 @@ class GraphExplorerService:
|
|||
pass
|
||||
|
||||
# Versuch 3c: Fallback - Lade alle Notes und filtere clientseitig (nur wenn Text-Suche fehlschlägt)
|
||||
# OPTIMIERUNG: Verwende einen globalen Cache für alle Notes-Titel, um Performance zu verbessern
|
||||
# Dies ist langsamer, aber findet auch Notes, die die Text-Suche nicht findet
|
||||
if possible_title_norm and len(possible_title_norm) > 5:
|
||||
try:
|
||||
# Lade eine größere Anzahl von Notes (nur wenn nötig)
|
||||
res_all, _ = self.client.scroll(
|
||||
collection_name=self.notes_col,
|
||||
limit=200, # Begrenzt, um Performance zu gewährleisten
|
||||
with_payload=True
|
||||
)
|
||||
if res_all:
|
||||
for r in res_all:
|
||||
if r.payload:
|
||||
note_title = r.payload.get("title", "")
|
||||
note_title_norm = normalize_title(note_title)
|
||||
if note_title_norm and possible_title_norm:
|
||||
if (note_title_norm == possible_title_norm or
|
||||
note_title_norm.startswith(possible_title_norm) or
|
||||
possible_title_norm.startswith(note_title_norm)):
|
||||
self._note_cache[r.payload['note_id']] = r.payload
|
||||
return r.payload
|
||||
# Lade alle Notes (einmalig, dann Cache) - OPTIMIERT mit paginierter Suche
|
||||
if not hasattr(self, '_all_notes_cache') or not self._all_notes_cache:
|
||||
self._all_notes_cache = {} # note_id -> payload
|
||||
self._all_notes_title_map = {} # normalisierter Titel -> Liste von Notes
|
||||
|
||||
# Paginierte Suche, um ALLE Notes zu laden
|
||||
next_offset = None
|
||||
total_loaded = 0
|
||||
while True:
|
||||
res_all, next_offset = self.client.scroll(
|
||||
collection_name=self.notes_col,
|
||||
limit=1000,
|
||||
offset=next_offset,
|
||||
with_payload=True
|
||||
)
|
||||
for r in res_all:
|
||||
if r.payload:
|
||||
note_id = r.payload.get('note_id')
|
||||
note_title = r.payload.get("title", "")
|
||||
if note_id and note_title:
|
||||
self._all_notes_cache[note_id] = r.payload
|
||||
# Normalisiere Titel und speichere Mapping
|
||||
note_title_norm_cached = normalize_title(note_title)
|
||||
if note_title_norm_cached:
|
||||
if note_title_norm_cached not in self._all_notes_title_map:
|
||||
self._all_notes_title_map[note_title_norm_cached] = []
|
||||
self._all_notes_title_map[note_title_norm_cached].append(r.payload)
|
||||
total_loaded += 1
|
||||
if next_offset is None:
|
||||
break
|
||||
|
||||
# Suche im Cache (verwende _all_notes_title_map statt _all_notes_cache)
|
||||
if hasattr(self, '_all_notes_title_map') and possible_title_norm in self._all_notes_title_map:
|
||||
matches = self._all_notes_title_map[possible_title_norm]
|
||||
if matches:
|
||||
# Nimm das erste Match
|
||||
result = matches[0]
|
||||
self._note_cache[result['note_id']] = result
|
||||
self._ref_resolution_cache[ref_str] = result
|
||||
return result
|
||||
|
||||
# Fallback: Durchsuche alle normalisierten Titel
|
||||
if hasattr(self, '_all_notes_title_map'):
|
||||
for norm_title, notes_list in self._all_notes_title_map.items():
|
||||
if isinstance(notes_list, list) and notes_list:
|
||||
if (norm_title == possible_title_norm or
|
||||
norm_title.startswith(possible_title_norm) or
|
||||
possible_title_norm.startswith(norm_title)):
|
||||
result = notes_list[0]
|
||||
self._note_cache[result['note_id']] = result
|
||||
self._ref_resolution_cache[ref_str] = result
|
||||
return result
|
||||
except Exception:
|
||||
pass
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user