Notas para uno mismo. El código es público, los datos no.
- Bearer token único (
ACCESS_TOKEN). Todo endpoint salvo/api/healthlo requiere. Se valida con comparación de strings constante por tamaño en el Worker. - CORS allowlist explícita. Solo
evolvea.pages.dev, sus previews*.evolvea.pages.devylocalhostpueden recibir respuesta del navegador. Otros orígenes se ignoran (no se devuelveAccess-Control-Allow-Origin). - Rate limiting in-memory por IP dentro del Worker:
- Sin auth válida: 10 req / min / IP
- Endpoints LLM (caros): 30 req / min / IP
- Resto autenticados: 200 req / min / IP
- Limitación: cada isolate de Cloudflare tiene su propio mapa. Para máxima dureza, activar Rate Limiting Rules en el dashboard de Cloudflare a nivel de zona/worker.
- Cifrado en reposo para credenciales Garmin (AES-GCM con
ENCRYPTION_KEY). Nunca se devuelven al cliente. - Whitelist de columnas escribibles en
db.updateProfile(). Defiende contra inyección por nombre de columna en el PATCH del perfil.
GET /api/profile strip-ea estos campos antes de responder:
llm_api_key,nutrition_api_keygarmin_email_enc,garmin_password_enc
Las API keys de los LLM siempre las usa el Worker server-side (env.OPENROUTER_API_KEY, env.ANTHROPIC_API_KEY, etc.).
Si crees que se ha filtrado el token (lo viste en una captura, lo metiste en un repo público sin querer, etc.):
# 1. Genera uno nuevo
openssl rand -base64 48
# 2. Pégalo en api/.dev.vars (reemplaza la línea ACCESS_TOKEN=...)
# 3. Sube al Worker:
cd api
echo "$NUEVO_TOKEN" | npx wrangler secret put ACCESS_TOKEN
# 4. Actualízalo en el cliente. En la app, ve a Ajustes → Conexión
# (o ejecuta en la consola del navegador):
localStorage.setItem('rjj_token', 'EL_NUEVO_TOKEN');- Suplantación si pierdes el token: si el token cae, el atacante tiene acceso total a tus datos. Rota.
- DDoS distribuido: el rate limit in-memory es per-isolate. Un atacante con muchas IPs distintas puede saltárselo. Mitigación: Cloudflare rate-limiting rules a nivel zona (gratis hasta 10k req/mes).
- Cosechado de respuestas de IA: si el token cae, el atacante puede gastar tu cupo de OpenRouter. Mitigación: poner un límite de gasto en OpenRouter.
Si encuentras un fallo de seguridad, abre un issue privado en GitHub o escríbeme a rjj@proars.com.