/** * Middleware CORS - Se ejecuta ANTES de la autenticación * * Maneja las solicitudes OPTIONS (preflight) para rutas de API externa * y agrega headers CORS a las respuestas. * * Solo permite origenes de *.nucleoriofrio.com y localhost (dev) */ // Rutas que necesitan CORS (API externa) const CORS_ROUTES = [ '/api/messages/send', '/api/mcp' ] // Validar si el origen está permitido function isAllowedOrigin(origin: string | undefined): boolean { if (!origin) return false // Permitir cualquier subdominio de nucleoriofrio.com if (origin.match(/^https?:\/\/([a-z0-9-]+\.)?nucleoriofrio\.com$/)) { return true } // Permitir localhost para desarrollo if (origin.match(/^http:\/\/localhost(:\d+)?$/)) { return true } return false } export default defineEventHandler((event) => { const path = getRequestURL(event).pathname // Solo aplicar a rutas que necesitan CORS const needsCors = CORS_ROUTES.some(route => path.startsWith(route)) if (!needsCors) { return } const origin = getHeader(event, 'origin') // Si el origen está permitido, agregar headers CORS if (isAllowedOrigin(origin)) { setResponseHeaders(event, { 'Access-Control-Allow-Origin': origin!, 'Access-Control-Allow-Methods': 'GET, POST, PUT, DELETE, OPTIONS', 'Access-Control-Allow-Headers': 'Content-Type, Authorization', 'Access-Control-Allow-Credentials': 'true', 'Access-Control-Max-Age': '86400' // Cache preflight por 24 horas }) } // Si es una solicitud OPTIONS (preflight), responder inmediatamente if (getMethod(event) === 'OPTIONS') { // Responder con 204 No Content setResponseStatus(event, 204) return '' } })