5.0 KiB
5.0 KiB
🎯 Motor de Recomendações
Filosofia
"Não precisas de IA para parecer inteligente. Precisas de regras bem pensadas."
O motor de recomendações evolui em 3 fases:
| Fase | Tecnologia | Estado |
|---|---|---|
| 1 — Regras estáticas | Lógica JS simples | ✅ MVP |
| 2 — IA de linguagem | OpenAI API | 🔲 Fase 2 |
| 3 — Recomendação personalizada | Histórico + ML | 🔲 Fase 3 |
FASE 1 — Regras Estáticas (MVP)
Contextos disponíveis
O utilizador escolhe um dos seguintes contextos:
// constants/contexts.js
export const CONTEXTS = [
{
id: 'travel_short',
label: 'Viagem curta (1-3 dias)',
icon: '✈️',
tags: ['travel'],
priorityCategories: ['documents', 'clothing', 'electronics', 'footwear'],
maxItems: 20,
},
{
id: 'travel_long',
label: 'Viagem longa (4+ dias)',
icon: '🧳',
tags: ['travel'],
priorityCategories: ['documents', 'clothing', 'electronics', 'footwear', 'accessories'],
maxItems: 40,
},
{
id: 'work',
label: 'Dia de trabalho',
icon: '💼',
tags: ['work'],
priorityCategories: ['electronics', 'clothing', 'footwear', 'accessories'],
maxItems: 15,
},
{
id: 'casual',
label: 'Fim de semana casual',
icon: '😎',
tags: ['casual'],
priorityCategories: ['clothing', 'footwear', 'accessories'],
maxItems: 10,
},
{
id: 'sport',
label: 'Treino / Desporto',
icon: '🏃',
tags: ['sport'],
priorityCategories: ['clothing', 'footwear'],
maxItems: 8,
},
{
id: 'outdoor',
label: 'Saída para o exterior',
icon: '🌲',
tags: ['outdoor', 'travel'],
priorityCategories: ['clothing', 'footwear', 'accessories'],
maxItems: 12,
},
];
Lógica de filtragem
// services/suggestions.js
export function getSuggestionsForContext(items, contextId) {
const context = CONTEXTS.find(c => c.id === contextId);
if (!context) return [];
// 1. Filtrar itens com pelo menos uma tag do contexto
const relevantItems = items.filter(item =>
item.contextTags.some(tag => context.tags.includes(tag))
);
// 2. Ordenar por prioridade de categoria
const sorted = relevantItems.sort((a, b) => {
const aIndex = context.priorityCategories.indexOf(a.category);
const bIndex = context.priorityCategories.indexOf(b.category);
const aPriority = aIndex === -1 ? 999 : aIndex;
const bPriority = bIndex === -1 ? 999 : bIndex;
return aPriority - bPriority;
});
// 3. Limitar ao máximo de itens
return sorted.slice(0, context.maxItems);
}
Exemplos de output
Contexto: "Viagem curta"
✅ Passaporte (documents.identity → travel)
✅ Portátil (electronics.computers → travel, work)
✅ Carregador USB-C (electronics.cables → travel)
✅ T-shirt preta (clothing.casual → casual, travel)
✅ Jeans azul (clothing.casual → casual, travel)
✅ Sapatilhas brancas (footwear.casual → casual, travel)
❌ Fato de treino (clothing.sportswear → sport) ← não aparece
❌ Consola PS5 (electronics.gaming → casual) ← não aparece
FASE 2 — IA de Linguagem (OpenAI API)
Não implementar no MVP. Esta secção é referência para a Fase 2.
Objetivo
Permitir ao utilizador escrever em linguagem natural:
- "Vou viajar 4 horas de comboio"
- "Tenho uma reunião importante amanhã de manhã"
- "Fim de semana na praia"
Arquitetura proposta
Utilizador escreve frase
↓
OpenAI API (classificação de contexto)
↓
Retorna JSON estruturado:
{
"context": "travel",
"duration": "short",
"environment": "transit",
"weather": "unknown",
"formality": "casual"
}
↓
Motor de regras Fase 1 (com parâmetros enriquecidos)
↓
Lista de itens sugeridos
Prompt base para OpenAI
System: És um assistente de inventário pessoal.
Analisa a frase do utilizador e devolve APENAS um JSON com:
- context: "travel" | "work" | "casual" | "sport" | "outdoor" | "formal"
- duration: "short" | "medium" | "long" | null
- environment: "indoor" | "outdoor" | "transit" | null
- weather: "cold" | "hot" | "rainy" | null
- formality: "casual" | "formal" | null
User: {frase do utilizador}
FASE 3 — Recomendação Personalizada
Fase muito futura. Apenas visão.
- Sistema aprende quais itens o utilizador seleciona/ignora das sugestões
- Pontuação de relevância por item por contexto
- Integração com API de clima para filtros automáticos
- Histórico de viagens para sugestões baseadas em padrões
Notas para o agente IA
- No MVP, usar APENAS a Fase 1. Não implementar OpenAI no MVP.
- A lógica de
getSuggestionsForContextdeve ser pura (sem side effects) - Os contextos são fixos no MVP — não adicionar sem validar com o utilizador
- A ordenação por
priorityCategoriesé intencional e importante — respeitá-la - Quando a Fase 2 for implementada, o output do OpenAI deve mapear para os IDs de contexto da Fase 1