From 1e41c1c07ccf2cfc45a22622eac91a27cb2ac791 Mon Sep 17 00:00:00 2001 From: Matt Date: Sat, 28 Mar 2026 14:49:56 +0100 Subject: [PATCH] fix: use predefined values for tool calls, improve completion flow - System prompt now specifies exact predefined values for services/industries/timelines - Agent instructed to call complete_brief IMMEDIATELY when name+email confirmed - Chip labels fall back to raw value for unknown keys instead of showing i18n path - Added completion transition logging Co-Authored-By: Claude Opus 4.6 (1M context) --- src/components/configurator/VoiceAgent.tsx | 19 ++++++++++++++----- src/lib/gemini-live.ts | 18 ++++++++++++++---- 2 files changed, 28 insertions(+), 9 deletions(-) diff --git a/src/components/configurator/VoiceAgent.tsx b/src/components/configurator/VoiceAgent.tsx index f4c8a3b..b47b56c 100644 --- a/src/components/configurator/VoiceAgent.tsx +++ b/src/components/configurator/VoiceAgent.tsx @@ -75,7 +75,9 @@ export default function VoiceAgent({ locale, onComplete }: VoiceAgentProps) { // Handle completion useEffect(() => { if (completedBrief && completedFormData) { + console.log('[VoiceAgent] Brief complete, transitioning in 1.5s...'); const timer = setTimeout(() => { + console.log('[VoiceAgent] Calling onComplete'); onComplete(completedBrief, completedFormData); }, 1500); return () => clearTimeout(timer); @@ -94,23 +96,30 @@ export default function VoiceAgent({ locale, onComplete }: VoiceAgentProps) { ['0px 0px 0px rgba(0,100,148,0)', '0px 0px 30px rgba(0,100,148,0.3)'], ); - // Build selection chips + // Build selection chips — use i18n for known keys, raw value otherwise + const KNOWN_SERVICES = ['web', 'systems', 'infrastructure']; + const KNOWN_AI_TYPES = ['teammate', 'customer-facing', 'data-intelligence', 'notsure']; + const KNOWN_INDUSTRIES = ['maritime', 'hospitality', 'technology', 'realestate', 'finance', 'ngo', 'other']; + const KNOWN_TIMELINES = ['asap', '1-3months', '3-6months', 'exploring']; + const chipLabels: string[] = []; if (selections.services) { for (const svc of selections.services) { - try { chipLabels.push(t(`services.${svc}.title`)); } catch { chipLabels.push(svc); } + chipLabels.push(KNOWN_SERVICES.includes(svc) ? t(`services.${svc}.title`) : svc); } } if (selections.aiEnabled && selections.aiTypes) { for (const ai of selections.aiTypes) { - try { chipLabels.push(t(`aiTypes.${ai}.title`)); } catch { chipLabels.push(ai); } + chipLabels.push(KNOWN_AI_TYPES.includes(ai) ? t(`aiTypes.${ai}.title`) : ai); } } if (selections.industry) { - try { chipLabels.push(t(`industries.${selections.industry}`)); } catch { chipLabels.push(selections.industry); } + const ind = selections.industry; + chipLabels.push(KNOWN_INDUSTRIES.includes(ind) ? t(`industries.${ind}`) : ind); } if (selections.timeline) { - try { chipLabels.push(t(`timelines.${selections.timeline}`)); } catch { chipLabels.push(selections.timeline); } + const tl = selections.timeline; + chipLabels.push(KNOWN_TIMELINES.includes(tl) ? t(`timelines.${tl}`) : tl); } return ( diff --git a/src/lib/gemini-live.ts b/src/lib/gemini-live.ts index 34df263..34c1cc2 100644 --- a/src/lib/gemini-live.ts +++ b/src/lib/gemini-live.ts @@ -93,9 +93,14 @@ Ton rôle est de guider naturellement la conversation à travers les sujets suiv 7. Enfin, leur prénom, nom et adresse e-mail pour envoyer le brief Instructions : -- Appelle update_selections chaque fois qu'un point est confirmé dans la conversation. +- Appelle update_selections chaque fois qu'un point est confirmé. Utilise UNIQUEMENT ces valeurs prédéfinies : + - services : "web", "systems", "infrastructure" + - aiTypes : "teammate", "customer-facing", "data-intelligence", "notsure" + - industry : "maritime", "hospitality", "technology", "realestate", "finance", "ngo", "other" + - timeline : "asap", "1-3months", "3-6months", "exploring" + Associe ce que l'utilisateur dit à la valeur prédéfinie la plus proche. - Appelle analyze_website dès que l'utilisateur fournit une URL — puis intègre naturellement les résultats dans la discussion. -- Appelle complete_brief une fois que le nom et l'e-mail sont confirmés. +- Appelle complete_brief IMMÉDIATEMENT dès que le nom et l'e-mail sont confirmés. N'attends pas — appelle l'outil tout de suite. Dis quelque chose comme "Parfait, je génère votre brief maintenant". - Garde tes réponses concises : 2 à 3 phrases maximum par tour. - Sois chaleureux, direct et professionnel — jamais générique. @@ -121,9 +126,14 @@ Your role is to walk through the following topics naturally in conversation: 7. Finally, their name and email to send the brief Instructions: -- Call update_selections each time a data point is confirmed during the conversation. +- Call update_selections each time a data point is confirmed. Use ONLY these predefined values: + - services: "web", "systems", "infrastructure" + - aiTypes: "teammate", "customer-facing", "data-intelligence", "notsure" + - industry: "maritime", "hospitality", "technology", "realestate", "finance", "ngo", "other" + - timeline: "asap", "1-3months", "3-6months", "exploring" + Map what the user says to the closest predefined value. - Call analyze_website as soon as the user provides a URL — then discuss the findings naturally. -- Call complete_brief once name and email are confirmed. +- Call complete_brief IMMEDIATELY once you have confirmed the user's name and email. Do not wait — call the tool right away. Say something like "Great, I'm generating your brief now" while calling the tool. - Keep responses concise: 2–3 sentences maximum per turn. - Be warm, direct, and professional — never generic.