From b742d774c85c218dcd03996206d1de394c1d23ca Mon Sep 17 00:00:00 2001 From: Rodribm10 Date: Sun, 19 Apr 2026 08:06:31 -0300 Subject: [PATCH] fix(captain-memory): block suite hallucinations + hardcode cadastral data exclusion MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Real test revealed gpt-4o-mini was still: - Hallucinating suite names ("Aluba" doesn't exist — we only have Alexa, Stilo, Hidromassagem) - Extracting cadastral data as memory ("Rodrigo has a CPF", "Name is X") despite the per-type NÃO examples Added two sections at the top of the prompt: 1. Business canonical data — explicit whitelist of suite names (Alexa, Stilo, Hidromassagem) and stay types. Anything else = discard, NO auto- normalization. LLM must not guess. 2. Cadastral data absolute rule — explicit list of fields that are profile data, not memory: name, CPF/RG/passport, email/phone/address, birth date. Plus 5 concrete ❌ examples of what was being wrongly extracted in the wild. Existing 9 specs still pass (stub at call_llm; prompt change is semantic, not structural). Co-Authored-By: Claude Opus 4.7 (1M context) --- .../contact_memories/extraction_service.rb | 20 +++++++++++++++++++ 1 file changed, 20 insertions(+) diff --git a/enterprise/app/services/captain/contact_memories/extraction_service.rb b/enterprise/app/services/captain/contact_memories/extraction_service.rb index baab96c02..288d861b4 100644 --- a/enterprise/app/services/captain/contact_memories/extraction_service.rb +++ b/enterprise/app/services/captain/contact_memories/extraction_service.rb @@ -38,6 +38,26 @@ class Captain::ContactMemories::ExtractionService <<~PROMPT Você é um analista conservador que extrai apenas FATOS MEMORÁVEIS de uma conversa de WhatsApp entre um hóspede e um hotel. Sua missão é criar memória útil de longo prazo sobre o cliente — não transcrever a conversa. + ## CONTEXTO DO NEGÓCIO (dados canônicos — NÃO invente fora desta lista) + + - **Suítes válidas**: APENAS `Alexa`, `Stilo`, `Hidromassagem`. Se o texto mencionar qualquer outro nome de suíte (ex: "Aluba", "Premium", "Deluxe"), é ERRO de transcrição ou alucinação — DESCARTE o fato. Nunca normalize pra um dos 3 nomes automaticamente: se o cliente disse "queria a Aluba", descarte silenciosamente. + - **Permanências válidas**: `2hrs`, `3hrs`, `4hrs`, `pernoite`, `diária`. Qualquer outro termo = descarte. + + ## DADOS CADASTRAIS NÃO SÃO MEMÓRIA (regra absoluta) + + Os seguintes dados são armazenados separadamente no perfil do contato e NUNCA devem virar memória: + - Nome completo / primeiro nome / apelido + - CPF, RG, passaporte, qualquer documento + - Email, telefone, endereço + - Data de nascimento (a não ser que esteja explicitamente vinculada a celebração no hotel — aí vira `data_comemorativa`, não cadastro) + + Exemplos de fatos INVÁLIDOS que NÃO devem ser extraídos: + - ❌ "Rodrigo tem um CPF que pode ser usado para reservas" + - ❌ "Cliente forneceu nome e CPF" + - ❌ "Rodrigo Borba Machado é o nome do cliente" + - ❌ "O email é x@y.com" + - ❌ "Informou telefone para contato" + ## TAXONOMIA ESTRITA Use apenas estes 9 tipos. Cada tipo tem definição precisa + exemplos do que SIM e do que NÃO é.