KI-Jobbasis, TTS und Bildvorschläge
Das CMS erzeugt Vorlese-Audios für Kategoriebezeichnungen, Storytitel sowie Text- und Linkinhalte von Stories. Audio und Wort-Zeitmarken sind Bestandteil des veröffentlichten Inhalts; die Joblogik bleibt unabhängig vom gewählten Audioanbieter. Die zugrunde liegende private Queue und der Adaptervertrag sind für TTS-, Bild- und Textjobs gemeinsam aufgebaut. TTS- und Bild-Lane besitzen produktive Worker; die Text-Lane ist für eine spätere Funktion vorbereitet.
Inhalt speichern
│
▼
Eingabe + Quell-Hash
│
▼
private KI-Queue mit getrennten Lanes: tts | image | text
│
├── TTS-Worker: pending → running → done / failed / cancelled
│ ├── Qwen3-TTS (lokales Python-Skript)
│ ├── KugelAudio
│ ├── ElevenLabs
│ └── Audio + Wort-Zeitmarken → Media Library
│ └── kompatible ttsJobs-Projektion am Inhalt
├── Bild-Worker: pending → running → done / failed / cancelled
│ ├── MFLUX / FLUX.2 klein (lokal auf Apple Silicon)
│ ├── fal.ai / GPT Image 2 oder FLUX Kontext Pro
│ ├── betreiberseitig gewählter HTTP-Endpunkt
│ └── privater Vorschlag → Auswahl → Media Library
└── Text-Lane (vorbereitet)Gemeinsames Jobmodell
Jeder KI-Job enthält Modalität, Lane, Operation, Zielinhalt, Dokument-ID, optionale numerische Entity-ID, Feldpfad, Locale, Eingabe-Hash, Status, Anzahl der Versuche, Queue-, Start- und Endzeit sowie Lease und Fehler. Ein stabiler Jobschlüssel verhindert doppelte offene Aufträge für dieselbe Operation am selben Ziel.
Modalitätsspezifische Ein- und Ausgaben liegen in Request- und Result-Payloads.
Generierte Dateien werden als Artefakte mit einem Zustand wie temporary,
proposal, accepted oder rejected referenziert. So können spätere Bild-
und Textfunktionen denselben Vertrag verwenden, ohne TTS-Felder vorzutäuschen.
Die Bild-Lane verwendet diesen Vertrag für mehrere private Vorschläge und ihre
redaktionelle Auswahl. Die Text-Lane besitzt noch keinen Worker und keine
redaktionelle Oberfläche.
Der gemeinsame Adaptervertrag deklariert Modalität, unterstützte Operationen und Abbruchfähigkeit. Sein Ergebnis kann Provider, Modell, Adapter- und Promptversion, technische Nutzungswerte und Provenienz enthalten. Die Queue speichert keine API-Schlüssel. Nutzungswerte dienen der Nachvollziehbarkeit; eine automatische Preis- oder Budgetberechnung findet nicht statt. Eine vorgesehene Lizenz wird nur als optionale Betreiberangabe protokolliert und nicht vom CMS rechtlich bewertet.
Für TTS erkennt der Eingabe-Hash, ob ein gespeichertes Audio noch zum aktuellen
Text passt. Audio, Wort-Zeitmarken und die für die App benötigten Metadaten
werden weiterhin als ttsJobs an Story oder Kategorie projiziert. Die zentrale
Queue gehört nicht zum öffentlichen Content-API-Vertrag und wird weder im
Content-Type Builder noch im Content Manager als redaktioneller Inhalt
angezeigt.
Automatische Auslöser
- Beim Anlegen einer Kategorie oder Story werden alle benötigten Jobs eingereiht.
- Beim Ändern einer Kategoriebezeichnung werden deren Jobs synchronisiert.
- Beim Ändern von Storytitel oder Slides werden die Storyjobs synchronisiert.
- Unveränderte Text-Hashes behalten ihr fertiges Audio; veränderte Felder
werden wieder auf
pendinggesetzt. - Veröffentlichen und Zurückziehen lösen keine neue Generierung aus.
- Eine Veröffentlichung wird abgewiesen, solange für die Locale Jobs den
Status
pendingoderrunninghaben.
Queue-Lanes und Worker
Die Lanes tts, image und text besitzen getrennte Einstellungen für
Parallelität, Lease-Dauer und Ausführungszeit. Dadurch blockiert ein langer Job
nicht automatisch andere Modalitäten. Innerhalb einer Lane reserviert ein
Worker den ältesten offenen Auftrag nach queuedAt und anschließend nach der
technischen ID. Ein bedingtes Update von pending auf running verhindert,
dass mehrere CMS-Instanzen denselben Auftrag gleichzeitig übernehmen. Die
TTS- und Bild-Worker laufen im Strapi-Prozess. Die Text-Lane stellt derzeit nur
die gemeinsame technische Basis bereit.
Jede Reservierung besitzt eine zeitlich begrenzte Lease. Ein aktiver Worker
verlängert sie während längerer Provideraufrufe. Beim regulären Herunterfahren
stellt der Worker seinen aktiven Auftrag sofort wieder auf pending. Beim Neustart
erkennt das CMS außerdem verwaiste Leases nicht mehr laufender Node-Prozesse auf
demselben Host und reiht sie erneut ein, ohne aktive Parallel-Worker anzutasten.
Nach einem harten Abbruch auf einem anderen Host greift spätestens die
Lease-Grenze; eine abgelaufene Lease wird ebenfalls wieder pending. Dieser
technische Retry behält queuedAt und damit die bisherige Queue-Position.
Manueller Retry und erzwungene Neugenerierung stellen einen Auftrag dagegen mit
einem neuen queuedAt hinten an; Cancel beendet ihn als cancelled.
Bildvorschläge und redaktionelle Übernahme
Für Kategorie- und Story-Icons sowie Bilder von Text-Slides startet die Redaktion die Generierung ausdrücklich an einem bereits angelegten Eintrag. Titel und Slide-Text werden dabei aus dem aktuellen Formular übernommen und müssen vor der Generierung nicht erneut gespeichert werden. Ein vollständig neuer Eintrag benötigt zunächst durch einmaliges Speichern eine technische Dokument-ID. Zielinhalt, Locale, Feldtyp, redaktionelle Zusatzanweisung und ein festes Stilprofil bilden die Eingabe. Die Stilprofile können betreiberseitig auf freigegebene Medien aus der Media Library verweisen. Ob der Betreiber ein lokales Modell oder eine API verwendet, ändert den redaktionellen Ablauf nicht. Unterstützte Rasterbilder und SVG-Dateien werden für lokale Referenzaufrufe in größenbegrenzte PNG-Dateien umgewandelt; die ursprünglichen Medien bleiben unverändert.
Das Seitenpanel fasst offene Aufträge und verfügbare Vorschläge zusammen. Der eigentliche Workflow öffnet sich als Overlay und benennt die Felder mit ihrem inhaltlichen Kontext. Dort wählt die Redaktion das Bildfeld, eines der vom Betreiber freigeschalteten Modelle, die Vorschlagsanzahl und optional eine je Feld getrennte Bildanweisung. Nach der Generierung lässt sich der tatsächlich verwendete Prompt einsehen. Eine Bildanweisung dient zugleich als bearbeitbarer Ausgangspunkt für den Alternativtext; ohne Bildanweisung wird er aus dem Zielinhalt vorgeschlagen.
Ein Bildjob kann bis zu vier Vorschläge liefern. Sie bleiben außerhalb der Media Library in einem privaten Vorschlagsspeicher und sind nur über eine aktive Admin-Session mit passender Content-Manager-Berechtigung abrufbar. Erst die ausdrückliche Auswahl mit geprüftem Alternativtext lädt genau einen Vorschlag in die Media Library und setzt ihn in das Formular ein. Das Formular muss danach gespeichert werden. Ein vorher verwendetes Medium wird dabei weder automatisch überschrieben noch gelöscht.
Icons werden als quadratische Vollformatbilder mit Farbe bis an alle Dateiränder erzeugt. Eine defensive Randnormalisierung entfernt typische modellseitige Außenränder. Die einheitlichen rundlichen Ecken entstehen erst bei der Darstellung in der App, sodass kein weißer Hintergrund Bestandteil der Bilddatei wird.
Verwerfen, Abbruch, erneute Generierung, verlorene Leases und das Löschen des Zielinhalts entfernen nicht mehr benötigte private Dateien am jeweiligen Zustandswechsel. Es gibt keinen zeitgesteuerten Cleanup. Provider, Modell, Adapter- und Promptversion, technische Nutzung, Referenzmedien, Erzeugungszeit und redaktionelle Auswahl bleiben am privaten Job nachvollziehbar. Für ein übernommenes Medium wird zusätzlich ein privater Provenienzdatensatz angelegt, der die Zuordnung auch nach späteren Jobänderungen erhält. Eine konfigurierte Lizenz- oder Rechteangabe ist Metadatum und keine automatische rechtliche Freigabe.
Der fal.ai-Adapter verwendet die persistente Provider-Queue. Seine Request-ID
wird direkt nach dem Submit am Job gespeichert, damit ein CMS-Neustart denselben
externen Auftrag weiter abfragt und keine zweite kostenpflichtige Generierung
startet. Bei Abbruch und lokalem Timeout wird die externe Stornierung versucht.
Qualität, Ausgabegröße, Prompt und Anzahl der Referenzbilder beeinflussen die
Providerkosten. Das CMS speichert technische Nutzungsmetriken und vorhandene
fal-billableUnits. Aktuelle Einheitspreise werden ausschließlich serverseitig
beim Provider abgefragt. Einen Betrag zeigt die Admin-Oberfläche nur bei einem
festen Preis je Ergebnis oder auf Basis vergleichbarer abgeschlossener Aufträge.
Der dabei ermittelte Kosten-Snapshot bleibt am Queue-Job über Serverneustarts
hinweg erhalten. Das CMS führt weder ein Budget noch eine tatsächliche
Abrechnung.
Beim Start synchronisiert das CMS vorhandene ttsJobs idempotent in die
zentrale Queue. Die bestehende technische Strapi-UID und Tabelle bleiben für
Rolling Deployments erhalten, obwohl neue Zugriffe den gemeinsamen KI-Vertrag
verwenden. Dadurch bleiben ältere Datenexporte importierbar; vorhandene Audios,
Zeitmarken und abgeschlossene Zustände bleiben erhalten. Ein zuvor laufender
Job ohne gültige Lease wird erneut als pending eingereiht.
Medienbereinigung
Die Bereinigung läuft an den relevanten Zustandswechseln: nach Textänderung oder Neugenerierung, Recovery, Übernahme des veröffentlichten Audios, Publish und Löschen eines Inhalts sowie bei einem nicht festgeschriebenen Upload.
Vor dem Löschen prüft das CMS alle Draft- und Published-Stände von Stories und Kategorien sowie relevante Queue-Einträge. Gemeinsam verwendete oder noch veröffentlichte Audios bleiben erhalten. Das bisher veröffentlichte Audio wird daher während der Draft-Bearbeitung nicht gelöscht und erst nach dem Publish erneut geprüft. Bei Recover wird je Feld der neueste Fund übernommen; ältere unreferenzierte Kandidaten werden anschließend entfernt.
Zugriffsschutz
Status, Enqueue, Cancel, Recover, die Übernahme des veröffentlichten Audios und das zentrale Audio-Dashboard verwenden dieselbe aktive Admin-Session wie die Strapi-Oberfläche. Der Admin-Fetch-Client sendet das kurzlebige Zugriffstoken automatisch; ein eigenes TTS-Secret wird weder benötigt noch in das Browser-Bundle eingebettet. Öffentliche Requests, abgelaufene Sessions und Content-API-Tokens erhalten keinen Zugriff.
Nach der Authentifizierung greift Strapis Content-Manager-RBAC. Lesen von
Statusdaten erfordert read, Änderungen erfordern update für den jeweiligen
Content-Type. Das Dashboard setzt die Rechte für Stories und Kategorien
voraus. Verändernde Routen sind zusätzlich auf zehn Requests je Route und IP
innerhalb von 60 Sekunden begrenzt. Ein vorgeschalteter Reverse Proxy kann für
mehrere CMS-Instanzen ergänzend ein verteiltes Limit durchsetzen.
Locale-Konfiguration
Provideroptionen können pro vollständiger Locale, Sprache oder global gesetzt
werden. Für en-US gilt beispielsweise:
..._EN_US → ..._EN → globaler WertQwen3-TTS
Qwen wird über ein separates Python-Skript aufgerufen. Modellgewichte,
Python-Umgebung, Referenzaufnahmen und optionaler Forced Aligner werden nicht
mit npm install installiert. Für Voice Cloning muss das Transkript exakt zur
Referenzaufnahme passen. Der Forced Aligner liefert Wort-Zeitmarken; ohne
lokale GPU ist die Generierung je nach Modell deutlich langsamer.
KugelAudio
KugelAudio wird als Cloud-Dienst über API-Key, Modell und Voice-ID angebunden.
Die WebSocket-Übertragung ist der Standard, weil die Wort-Zeitmarken darüber
mitgeliefert werden. Mit KUGELAUDIO_REQUIRE_TIMESTAMPS=true gilt ein Audio
ohne Zeitmarken als fehlgeschlagen. Sample-Rate, Normalisierung, Sprache und
Stimme können global oder je Locale konfiguriert werden.
ElevenLabs
ElevenLabs erzeugt über die API PCM-Audio, das der Adapter als WAV speichert.
Für die in der App verwendete wortweise Hervorhebung ruft der Adapter bei
ELEVENLABS_FORCE_ALIGNMENT=true zusätzlich Forced Alignment auf. API-Key,
Voice-ID, Modell, Ausgabeformat und Sprachcode können global oder je Locale
gesetzt werden.
Änderungen an Worker, Lifecycle-Hooks, Wiederherstellung oder automatischem Löschen von Medien sind datenrelevant und benötigen gezielte Tests.