From d45eccea4777b81f940b6b366c4a7e9409a01b65 Mon Sep 17 00:00:00 2001 From: Matt Date: Tue, 3 Feb 2026 10:36:51 +0100 Subject: [PATCH] Add detailed logging to AI filtering for debugging Added console logging throughout the AI screening process to help diagnose issues when all projects get flagged. Logs model being used, batch processing, token usage, and actual error messages. Co-Authored-By: Claude Opus 4.5 --- src/server/services/ai-filtering.ts | 19 ++++++++++++++++--- 1 file changed, 16 insertions(+), 3 deletions(-) diff --git a/src/server/services/ai-filtering.ts b/src/server/services/ai-filtering.ts index 40d61f7..88c903f 100644 --- a/src/server/services/ai-filtering.ts +++ b/src/server/services/ai-filtering.ts @@ -274,6 +274,7 @@ export async function executeAIScreening( const openai = await getOpenAI() if (!openai) { // No OpenAI configured — flag all for manual review + console.warn('[AI Filtering] OpenAI client not available - API key may not be configured') for (const p of projects) { results.set(p.id, { meetsCriteria: false, @@ -287,6 +288,7 @@ export async function executeAIScreening( } const model = await getConfiguredModel() + console.log(`[AI Filtering] Using model: ${model} for ${projects.length} projects`) // Anonymize project data — use numeric IDs const anonymizedProjects = projects.map((p, i) => ({ @@ -319,6 +321,8 @@ ${JSON.stringify( Return your evaluation as JSON.` + console.log(`[AI Filtering] Processing batch ${Math.floor(i / batchSize) + 1}, ${batch.length} projects`) + const response = await openai.chat.completions.create({ model, messages: [ @@ -330,6 +334,8 @@ Return your evaluation as JSON.` max_tokens: 4000, }) + console.log(`[AI Filtering] Batch completed, usage: ${response.usage?.total_tokens} tokens`) + const content = response.choices[0]?.message?.content if (content) { try { @@ -344,6 +350,8 @@ Return your evaluation as JSON.` }> } + console.log(`[AI Filtering] Parsed ${parsed.projects?.length || 0} results from response`) + for (const result of parsed.projects) { const anon = batch.find((b) => b.project_id === result.project_id) if (anon) { @@ -356,8 +364,10 @@ Return your evaluation as JSON.` }) } } - } catch { + } catch (parseError) { // Parse error — flag batch for manual review + console.error('[AI Filtering] JSON parse error:', parseError) + console.error('[AI Filtering] Raw response content:', content.slice(0, 500)) for (const item of batch) { results.set(item.real_id, { meetsCriteria: false, @@ -368,15 +378,18 @@ Return your evaluation as JSON.` }) } } + } else { + console.error('[AI Filtering] Empty response content from API') } } - } catch { + } catch (error) { // OpenAI error — flag all for manual review + console.error('[AI Filtering] OpenAI API error:', error) for (const p of projects) { results.set(p.id, { meetsCriteria: false, confidence: 0, - reasoning: 'AI screening error — flagged for manual review', + reasoning: `AI screening error — flagged for manual review`, qualityScore: 5, spamRisk: false, })