// @requires classification.js fallback.js const promptItems = $('Code - Preparar Prompt IA').all(); const responseItems = $input.all(); return responseItems.map((responseItem, index) => { const original = (promptItems[index] && promptItems[index].json) || {}; const httpJson = responseItem.json || {}; if (httpJson.error) { return { json: { ...original, aiClassification: buildFallbackClassification('ai_error') } }; } let raw = null; try { const content = httpJson.choices && httpJson.choices[0] && httpJson.choices[0].message && httpJson.choices[0].message.content; raw = content ? JSON.parse(content) : null; } catch (e) { raw = null; } // Passa o ticket pra validacao poder aplicar a guarda deterministica "tecnico interno nunca // vira WAITING_VENDOR" (logic/classification.js -> isWaitingForInternalTechnician). Sem // isso a validacao so olha o JSON cru, nunca os fatos do proprio chamado. const validation = validateAiClassification(raw, original.ticket); let aiClassification; if (validation.valid) { aiClassification = validation.data; } else { // Motivo especifico e auditavel por que a IA caiu pra fallback -- nao joga tudo em // "invalid_json" (missao "correcao final", secao 9: decision_reason distinguivel). const isSemanticConflict = validation.errors.some((e) => e.includes('tecnico interno')); const isGenericAction = validation.errors.some((e) => e.includes('generico demais')); let reason = 'invalid_json'; if (isSemanticConflict) reason = 'ai_semantic_conflict'; else if (isGenericAction) reason = 'generic_or_unsupported_next_action'; aiClassification = buildFallbackClassification(reason); } return { json: { ...original, aiClassification } }; });