From 25ffb3727b082fe7f62c99c7cd6faf82704d33eb Mon Sep 17 00:00:00 2001 From: s4luorth Date: Sat, 29 Aug 2026 10:00:58 +0200 Subject: [PATCH] Scriptalizer: nach Zeichenlaenge batchen (32000-Limit) Fixe 18er-Batches sprengen bei langen/mehrseitigen Texten das InputText-Limit der Scriptalizer-API (32000 Zeichen) -> 'Input length limit 32000 exceeded'. Jetzt werden Batches nach kumulativer Zeichenlaenge (max 28000, Sicherheitsabstand) gebildet, die Anzahl 18 bleibt als zusaetzlicher Deckel. Co-Authored-By: Claude Opus 4.8 --- src/services/scriptalizer-service.js | 46 ++++++++++++++++++++-------- 1 file changed, 33 insertions(+), 13 deletions(-) diff --git a/src/services/scriptalizer-service.js b/src/services/scriptalizer-service.js index a1a1340..d0474b9 100644 --- a/src/services/scriptalizer-service.js +++ b/src/services/scriptalizer-service.js @@ -141,29 +141,49 @@ async function scriptalizeBatch(texts, font = "tilda", errFrequency = 10) { config.scriptalizer.fontMap[font.toLowerCase()] || config.scriptalizer.fontMap.tilda; const separator = config.scriptalizer.separator; - const BATCH_SIZE = 18; // 18 Texte pro Scriptalizer API Call (Scriptalizer-API-Limit: 32000 Zeichen pro Call → ca. 1700 Zeichen pro Brief sicher) + const BATCH_SIZE = 18; // Zusätzlicher Deckel: max. 18 Texte pro Call (unabhängig von der Länge). + // Primäre Grenze ist die ZEICHENLÄNGE: die Scriptalizer-API begrenzt den + // InputText auf 32000 Zeichen pro Call ("Input length limit 32000 exceeded"). + // Fixe 18er-Batches sprengen das bei langen (mehrseitigen) Texten – daher nach + // kumulativer Länge batchen, mit Sicherheitsabstand. + const MAX_BATCH_CHARS = 28000; + const sepLen = separator.length; + // Batches nach Länge (und max. Anzahl) bilden. + const batches = []; + { + let cur = []; + let curLen = 0; + for (const t of texts) { + const tLen = String(t || "").length; + const projected = curLen + (cur.length ? sepLen : 0) + tLen; + if (cur.length && (projected > MAX_BATCH_CHARS || cur.length >= BATCH_SIZE)) { + batches.push(cur); + cur = []; + curLen = 0; + } + cur.push(t); + curLen += (cur.length > 1 ? sepLen : 0) + tLen; + } + if (cur.length) batches.push(cur); + } + + const totalBatches = batches.length; console.log( - `[Scriptalizer] Processing ${texts.length} texts in batches of ${BATCH_SIZE}` + `[Scriptalizer] Processing ${texts.length} texts in ${totalBatches} batch(es) (max ${BATCH_SIZE} texts / ${MAX_BATCH_CHARS} chars each)` ); const allScriptalized = []; - // Teile in 25er Batches auf - for (let i = 0; i < texts.length; i += BATCH_SIZE) { - const batch = texts.slice(i, i + BATCH_SIZE); - const batchNumber = Math.floor(i / BATCH_SIZE) + 1; - const totalBatches = Math.ceil(texts.length / BATCH_SIZE); + for (let b = 0; b < batches.length; b += 1) { + const batch = batches[b]; + const batchNumber = b + 1; + const combinedText = batch.join(separator); console.log( - `[Scriptalizer] Processing batch ${batchNumber}/${totalBatches} (${ - batch.length - } texts, indices ${i}-${i + batch.length - 1})` + `[Scriptalizer] Processing batch ${batchNumber}/${totalBatches} (${batch.length} texts, ${combinedText.length} chars)` ); - // Kombiniere Texte mit Separator - const combinedText = batch.join(separator); - try { const result = await callScriptalizer( combinedText,