init
This commit is contained in:
72
backend/parser.py
Normal file
72
backend/parser.py
Normal file
@@ -0,0 +1,72 @@
|
||||
"""Zerlegt den rohen Feature-Text in Sektionen — nur für die Anzeige.
|
||||
|
||||
Format: titel (eine Zeile), ziel, dann wiederholbare <!-- funktion -->-Blöcke,
|
||||
denen <!-- regel -->-Blöcke zugeordnet werden, zuletzt sonstiges.
|
||||
Präambel, unbekannte Marker und Regeln ohne Funktion landen in `sonstiges`.
|
||||
Trennzeilen aus Bindestrichen (---) sind reine Optik und werden ignoriert.
|
||||
"""
|
||||
|
||||
import re
|
||||
|
||||
MARKER = re.compile(r"^<!--\s*([a-zä-ü]+)\s*-->\s*$")
|
||||
TRENNER = re.compile(r"^-{3,}\s*$")
|
||||
|
||||
|
||||
def zerlege(roh: str) -> dict:
|
||||
# Erst in Blöcke (schluessel, text) in Dateireihenfolge schneiden
|
||||
bloecke = []
|
||||
aktuell = None # None = Präambel vor dem ersten Marker
|
||||
puffer = []
|
||||
|
||||
def ablegen():
|
||||
text = "\n".join(z for z in puffer if not TRENNER.match(z)).strip()
|
||||
if text:
|
||||
bloecke.append((aktuell, text))
|
||||
puffer.clear()
|
||||
|
||||
for zeile in roh.splitlines():
|
||||
m = MARKER.match(zeile)
|
||||
if m:
|
||||
ablegen()
|
||||
aktuell = m.group(1)
|
||||
else:
|
||||
puffer.append(zeile)
|
||||
ablegen()
|
||||
|
||||
titel = []
|
||||
ziel = []
|
||||
funktionen = []
|
||||
sonstiges = []
|
||||
art = []
|
||||
for schluessel, text in bloecke:
|
||||
if schluessel == "titel":
|
||||
titel.append(text)
|
||||
elif schluessel == "art":
|
||||
art.append(text)
|
||||
elif schluessel == "ziel":
|
||||
ziel.append(text)
|
||||
elif schluessel == "funktion":
|
||||
funktionen.append({"text": text, "regeln": []})
|
||||
elif schluessel == "regel" and funktionen:
|
||||
funktionen[-1]["regeln"].append(text)
|
||||
else: # Präambel, unbekannter Marker, regel ohne funktion
|
||||
sonstiges.append(text)
|
||||
|
||||
# Titel ist eine Zeile: erste nicht-leere
|
||||
titel_zeilen = [z.strip() for t in titel for z in t.splitlines() if z.strip()]
|
||||
|
||||
# Funktionen-Bereich mit Markern rekonstruiert — für das Editor-Feld
|
||||
teile = []
|
||||
for f in funktionen:
|
||||
teile.append(f"<!-- funktion -->\n{f['text']}")
|
||||
for r in f["regeln"]:
|
||||
teile.append(f"<!-- regel -->\n{r}")
|
||||
|
||||
return {
|
||||
"titel": titel_zeilen[0] if titel_zeilen else "",
|
||||
"art": "optional" if art and art[0].strip().lower() == "optional" else "kern",
|
||||
"ziel": "\n\n".join(ziel),
|
||||
"funktionen": funktionen,
|
||||
"funktionen_roh": "\n".join(teile),
|
||||
"sonstiges": "\n\n".join(sonstiges),
|
||||
}
|
||||
Reference in New Issue
Block a user