refactor(brain): Fast-Path als Skill-Capability — fast_patterns im Manifest

Frueher: Spotify-spezifische Patterns hardcoded in agent.py — jeder neue
Steuer-Skill haette wieder Brain-Code-Aenderungen gebraucht.
Jetzt: jeder Skill deklariert seine eigenen Patterns im Manifest unter
fast_patterns: [{match, args, reply}]. Brain iteriert generisch, kein
Skill bekommt Sonderbehandlung.

- agent.py: _try_skill_fast_path liest aus skills.list_skills(), keine
  Spotify-Konstanten mehr. skill_create/skill_update Tool-Schema kennt
  fast_patterns (mit Beispiel + Wann-nutzen-Hinweis).
- skills.py: _normalize_fast_patterns validiert Regex + filtert kaputte
  Eintraege; create_skill/update_skill akzeptieren das Feld.
- main.py: einmalige Lifespan-Migration — wenn spotify-Skill existiert
  und kein fast_patterns hat, werden die alten Hardcoded-Patterns
  rueberkopiert. Idempotent, laeuft bei jedem Restart sicher mehrfach.
- seed_rules.py: neue Regel `seed/skill-rule/fast-patterns-for-control`
  erklaert ARIA wann sie das Feature nutzen soll (reines Steuern: ja,
  kreativer Output / Parametrisierung: nein) — mit Beispiel.

Trade-off: Volume-Patterns (lauter/leiser) fallen aus dem Fast-Path raus,
weil die Multi-Step-Logik (GET state → compute → PUT) sich nicht
deklarativ ausdruecken laesst. Wer das zurueck will: Spotify-Skill um
einen action=volume_relative-Arg erweitern der die Mathe intern macht.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
2026-06-06 08:56:15 +02:00
parent e04bbef361
commit 61c9183033
4 changed files with 231 additions and 111 deletions
+48
View File
@@ -131,6 +131,54 @@ SEED_RULES: List[dict] = [
"Skill-Friedhof und Stefan muss aufraeumen."
),
},
{
"migration_key": "seed/skill-rule/fast-patterns-for-control",
"type": "rule",
"title": "Skill-Regel: fast_patterns fuer reines Steuern (spart 5-10s Latenz)",
"category": "skills",
"content": (
"Wenn Du einen Skill baust oder aktualisierst, der **reine Steuer-"
"Befehle** behandelt (Licht an/aus, Spotify pause/next, Rollade "
"hoch/runter, Heizung +1°), trag ins Manifest `fast_patterns` ein. "
"Format pro Eintrag: `{match: \"^regex$\", args: {...}, reply: \"Text\"}`.\n"
"\n"
"Wirkung: das Brain matched eingehende User-Texte BEVOR Claude gerufen "
"wird. Match → run_skill(name, args) direkt → reply zurueck → Claude "
"uebersprungen. Stefan spart 5-10 Sekunden pro Befehl. Praktisch "
"Pflicht im Auto, wo Latenz nervt.\n"
"\n"
"REGELN beim Patterns schreiben:\n"
" - Mit `^` und `$` anchorn — sonst matched `pause` mitten in `pause "
"die musik dann erzaehl mir nen witz` und zerschiesst den Befehl.\n"
" - Case-insensitive (Brain matched mit re.IGNORECASE), Endsatzzeichen "
"werden vorher entfernt — schreibe Lowercase ohne Punkt.\n"
" - Mehrere Varianten = mehrere Eintraege (`^pause$`, `^pausiere$`, "
"`^stop$`). Sprachlich wechselt Stefan zwischen synonymen Kurzformen.\n"
" - reply = kurze Bestaetigung in genau einem Satz, gerne mit Emoji.\n"
"\n"
"NIE fast_patterns fuer:\n"
" - Skills mit kreativem Output (zusammenfassen, generieren, raten).\n"
" - Skills mit Parametern die aus Freitext extrahiert werden muessten "
" ('spiele jazz' geht nicht — was ist 'jazz'? Lass Claude entscheiden).\n"
" - Skills mit Multi-Step-Logik (z.B. Volumen +10 = erst Status holen, "
" rechnen, setzen). Wenn unbedingt: in den Skill-Code packen und "
" dem Skill einen `action`-Arg geben.\n"
"\n"
"Beispiel komplett:\n"
"```\n"
"fast_patterns = [\n"
" {\"match\": \"^pause$\",\n"
" \"args\": {\"path\": \"/v1/me/player/pause\", \"method\": \"PUT\"},\n"
" \"reply\": \"Spotify: pausiert ⏸\"}\n"
"]\n"
"```\n"
"\n"
"Stefan-Hinweis 06/2026: das war frueher hardcoded in agent.py fuer "
"Spotify und musste fuer jeden neuen Steuer-Skill nachgepflegt werden. "
"Jetzt steckt's pro Skill im Manifest — dein Job, ARIA, das gleich "
"mitzudenken wenn der Use-Case passt."
),
},
{
"migration_key": "seed/skill-rule/no-hardcoded-credentials",
"type": "rule",