all repos — red-anatomia @ 43cc40161c75c7c9bb5bef2c1ce2d551b7f24484

red-anatomia

src/knowledge/trilhas.ts (view raw)

 1
 2
 3
 4
 5
 6
 7
 8
 9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
import type { Detection } from '../core/types.js';
import { TECNOLOGIAS } from './tecnologias.js';

export function montarTrilha(deteccoes: Detection[]): string[] {
  const ancora = escolherAncora(deteccoes);
  const base = (ancora && TECNOLOGIAS[ancora]?.aprenderEmOrdem) || [
    'HTML semântico',
    'CSS (layout e responsividade)',
    'JavaScript moderno',
    'como o navegador conversa com o servidor (HTTP)',
  ];

  const passos = [...base];

  const temInfra = deteccoes.some(
    (d) => d.categorias.includes('CDN') || d.categorias.includes('PaaS'),
  );
  if (temInfra && !passos.some((p) => p.toLowerCase().includes('implanta'))) {
    passos.push('implantação e entrega (CDN, hospedagem/serverless)');
  }

  return dedup(passos);
}

function escolherAncora(deteccoes: Detection[]): string | undefined {
  const porCategoria = (cat: string) =>
    deteccoes
      .filter((d) => d.categorias.includes(cat))
      .sort((a, b) => b.confianca - a.confianca)[0]?.nome;

  return (
    porCategoria('Web frameworks') ??
    porCategoria('Static site generator') ??
    porCategoria('CMS') ??
    porCategoria('JavaScript frameworks') ??
    porCategoria('Ecommerce') ??
    porCategoria('JavaScript libraries')
  );
}

function dedup(itens: string[]): string[] {
  const vistos = new Set<string>();
  const saida: string[] = [];
  for (const item of itens) {
    const chave = item.toLowerCase();
    if (!vistos.has(chave)) {
      vistos.add(chave);
      saida.push(item);
    }
  }
  return saida;
}