Un microtest anónimo para descubrir afinidades entre estudiantes.
Translation pending
SocialGitHub @AmeliaDiOnlineOwner unconfirmed
Have you tried it? One tap is enough. No sign-in needed.
Repository information has not been collected yet.
No updates detected yet. GitHub releases will appear here.
que dios me salve
Translation pending
Taken from the repository README
Loading the full README.
Read the full README ↗Web app mobile-first para estudiantes de la ENES (UNAM) que conecta personas de forma anónima a partir de un cuestionario psicométrico. Cada persona recibe una identidad de animalito + color en pixel art y ve a sus afinidades como una constelación: los nodos compatibles se acercan y se unen. Hay dos pistas independientes, romance y amistad.
Es un proyecto estadístico, no una medida del valor de nadie: las afinidades son estimaciones reproducibles, todavía sin validar con datos reales de relaciones.
graph TD
A[Matrícula] -->|HMAC, nunca en claro| B[Sesión anónima]
B --> C[Cuestionario: 60 ítems + 3 filtros]
C --> D[Scoring y perfil: animal, color, narrativa]
D --> E[Recálculo global de afinidades]
E --> F[Resultado: lista y constelación]
E --> G[Notificaciones]
Hexagonal ligera, organizada por capas. Las reglas se aplican con ESLint
(no-restricted-imports); el detalle y el porqué están en
docs/ARQUITECTURA.md y docs/DECISIONES.md.
| Capa | Carpeta | Qué contiene | Puede importar |
|---|---|---|---|
| Configuración | src/config/ | Única carga de data/*.json, validada con Zod y congelada | types |
| Dominio | src/domain/ | Funciones puras: psychometrics, matching, explainability, identity, avatars, constellation, messages, shared | config, types |
| Contratos | src/contracts/ | DTOs que viajan por la API (servidor ↔ cliente) | domain (tipos) |
| Aplicación | src/application/ | Casos de uso, puertos, errores AppError, validación de entrada | domain, contracts, config |
| Infraestructura | src/infrastructure/ | Supabase (repositorios), seguridad, entorno, HTTP, raíz de composición | todo lo anterior |
| UI | src/ui/ | Componentes por feature: quiz, result, constellation, admin, entry, shared | contracts, domain de presentación, config |
| App | src/app/ | Páginas y rutas API delgadas: Zod → caso de uso → DTO | todo |
Reglas clave:
Date.now o Math.random. Reloj, HMAC y semillas se
inyectan (Clock, Hmac, mulberry32).Result<T, E>; las rutas los traducen a HTTP en un solo lugar
(infrastructure/http/responses.ts), con mensaje es-MX y un code estable.data/microtest.json: ítems y escala Likert.data/matching-config.json: umbrales, pesos, dimensiones y cupos por pista.data/arquetipos.json: 103 animales × 55 colores.data/enneagram*.json: prototipos del Eneagrama.Para cambiar umbrales o pesos se edita el JSON, no el código; npm run data:validate lo
comprueba. El modelo y su calibración se describen en docs/SCORING.md.
Una sola migración, supabase/migrations/00000000000000_base.sql,
más supabase/seed.sql para el catálogo.
profiles, quiz_responses, matches, notifications) no
tienen permisos para anon ni authenticated. El servidor las lee con el service role
después de verificar la sesión.NULL. Todas fijan
search_path = ''.replace_matches publica el conjunto de matches de forma atómica y rechaza resultados
calculados sobre una versión vieja del grupo de perfiles.Requisitos: Node 24, y Docker + Supabase CLI para la base local.
npm install
supabase start
npm run db:reset # migración base + semilla
npm run dev # http://localhost:3000
| Script | Qué hace |
|---|---|
npm run check | escaneo de secretos + lint + typecheck + tests (lo que debe estar en verde antes de cada commit) |
npm run secrets:check | busca claves (Firecrawl, Supabase, JWT…) en archivos rastreados y logs; npm run hooks:install activa el hook de pre-commit |
npm run data:literature | crawler de literatura: dry-run por defecto; -- --run gasta créditos de Firecrawl dentro de los topes (ver docs/LITERATURA.md) |
npm run lint / typecheck / test | por separado |
npm run data:validate | valida data/*.json, el catálogo y el contrato SQL ↔ TypeScript |
npm run db:reset | reinicia la base local con la migración base y la semilla |
npm run db:apply | aplica migración + semilla a un proyecto Supabase remoto vacío vía Management API (SUPABASE_ACCESS_TOKEN en .env.local); -- --status cuenta filas |
npm run build | build de producción |
Las variables de entorno están en .env.example y se validan con Zod en
src/infrastructure/env/. El despliegue (Supabase remoto, Vercel, Upstash) está en
DESPLIEGUE.md; la operación del panel, en
MANUAL_ADMINISTRADOR.md.
Rutas de desarrollo (devuelven 404 en producción): /dev/sprites, /dev/ui,
/dev/constellation y /dev/physics (afinación de la física; ver docs/FISICA.md).
/api/enter
responde igual para cuentas nuevas y existentes.SECURITY DEFINER.withApiSecurity: origen permitido, rate limit (Upstash) y
cabeceras no-store. CSP y HSTS se definen en next.config.ts.supabase/purge_event.sql borra a todas las personas participantes al cerrar el evento y
conserva las cuentas de administración.| Documento | Para qué |
|---|---|
docs/ARQUITECTURA.md | Auditoría, capas y plan de unificación |
docs/DECISIONES.md | ADRs cortos: qué se decidió y por qué |
docs/SCORING.md | Modelo de scoring y matching actual |
docs/ESTADO_ACTUAL.md | Estado y plan de la integración HEXACO por capas |
docs/EVIDENCIA.md · docs/LITERATURA.md | Matriz de evidencia y pipeline de literatura (Firecrawl + APIs abiertas) |
docs/AUDIT.md | Auditoría previa a la unificación (histórica) |
docs/CONTEXTO_PROYECTO.md | Contexto extenso previo a la unificación (histórico; las rutas src/lib/* ya no existen) |
DESPLIEGUE.md · MANUAL_ADMINISTRADOR.md |
.qoder/ y .kiro/ son artefactos de herramientas externas y no describen la estructura
actual.
any, sin @ts-ignore. TypeScript con strict, noUncheckedIndexedAccess y
exactOptionalPropertyTypes.npm run check en verde en cada uno.NO_MATCH_MESSAGE está fijado por tests: no se cambia sin una decisión explícita.| Operación |