From c19f071acced554beef09d3a61d4cc18b57faacf Mon Sep 17 00:00:00 2001 From: Benjamin Sutter Date: Sun, 30 Aug 2026 19:18:11 +0200 Subject: [PATCH] =?UTF-8?q?feat(livia):=20Modell=20und=20Textl=C3=A4nge=20?= =?UTF-8?q?=C3=BCber=20Umgebungsvariablen=20einstellbar?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Das Modell stand fest im Code, obwohl es die grösste Kostenstellschraube ist — ein Lauf über fünfzig Meldungen kostet mit Opus 5 rund 0.40 USD, mit Haiku 4.5 etwa 0.08. Wer die Anwendung betreibt, soll diese Abwägung treffen können, ohne den Quelltext anzufassen und neu zu deployen. `LIVIA_RESEARCH_MODEL` wählt das Modell, `LIVIA_RESEARCH_TEXT_LIMIT` die Menge Artikeltext je Meldung — der zweite grosse Hebel, weil der Immobilienbezug einer Firmenmeldung fast immer im ersten Absatz steht und jede Halbierung die Eingabekosten halbiert. Beide haben Vorgabewerte; ohne gesetzte Variablen verhält sich alles wie bisher. Co-Authored-By: Claude Opus 5 (1M context) --- api/_lib/researchAnalysis.ts | 27 +++++++++++++++++++++++++-- 1 file changed, 25 insertions(+), 2 deletions(-) diff --git a/api/_lib/researchAnalysis.ts b/api/_lib/researchAnalysis.ts index a900792..8b9ef93 100644 --- a/api/_lib/researchAnalysis.ts +++ b/api/_lib/researchAnalysis.ts @@ -90,6 +90,29 @@ function extractJson(text: string): unknown { */ const BATCH_SIZE = 5 +/** + * Welches Modell die Einordnung vornimmt. + * + * Über `LIVIA_RESEARCH_MODEL` umstellbar, ohne den Code anzufassen — die + * Wahl ist eine Kosten- und Qualitätsabwägung und gehört damit dem Betreiber, + * nicht dem Quelltext. + * + * Grössenordnung je Lauf über rund fünfzig Meldungen: + * claude-opus-5 ≈ 0.40 USD stärkstes Urteil + * claude-sonnet-5 ≈ 0.20 USD + * claude-haiku-4-5 ≈ 0.08 USD für eine Ja/Nein-Einordnung meist ausreichend + */ +const MODEL = process.env.LIVIA_RESEARCH_MODEL ?? 'claude-opus-5' + +/** + * Wie viel Artikeltext das Modell zu lesen bekommt. + * + * Ebenfalls umstellbar, weil es der zweite grosse Kostenhebel ist: Der + * Immobilienbezug einer Firmenmeldung steht fast immer im ersten Absatz, und + * jede Halbierung halbiert die Eingabekosten. + */ +const TEXT_LIMIT = Number(process.env.LIVIA_RESEARCH_TEXT_LIMIT ?? 2000) + /** * Wie viele Teilstapel gleichzeitig beurteilt werden. * @@ -116,12 +139,12 @@ async function analyzeBatch( `Quelle: ${it.source}`, `Titel: ${it.title}`, it.publishedAt ? `Publiziert: ${it.publishedAt}` : '', - `Text: ${it.text.slice(0, 2000)}`, + `Text: ${it.text.slice(0, TEXT_LIMIT)}`, ].filter(Boolean).join('\n')) .join('\n\n') const response = await client.messages.create({ - model: 'claude-opus-5', + model: MODEL, max_tokens: 8000, system: SYSTEM_PROMPT, // Einordnen ist bei fünf Einträgen eine Routineaufgabe — die niedrige Stufe