import { existsSync } from 'node:fs'; import { resolve } from 'node:path'; /** Rutas de los archivos de certificado (se leen al arrancar). Con `pfx` o con `key` + `cert`. */ export interface HttpsConfig { pfxPath?: string; passphrase?: string; keyPath?: string; certPath?: string; } export interface AppConfig { port: number; webOrigin: string; serviceLayer: { url: string; companyDb: string; rejectUnauthorized: boolean; }; dbType: 'HANA' | 'MSSQL'; cookieSecure: boolean; /** Carpeta con el build de Angular que la API sirve; null si no existe (desarrollo con `ng serve`). */ webDistDir: string | null; /** null = la API escucha en HTTP. */ https: HttpsConfig | null; /** Si hay HTTPS: puerto HTTP que redirige al HTTPS (por ejemplo 80). null = no se abre. */ httpRedirectPort: number | null; } const vacio = (v: string | undefined): string | undefined => (v && v.trim() !== '' ? v.trim() : undefined); function leerHttps(): HttpsConfig | null { const pfxPath = vacio(process.env.HTTPS_PFX_PATH); const keyPath = vacio(process.env.HTTPS_KEY_PATH); const certPath = vacio(process.env.HTTPS_CERT_PATH); if (!pfxPath && !keyPath && !certPath) return null; if (pfxPath && (keyPath || certPath)) { throw new Error('Configure el certificado con HTTPS_PFX_PATH o con HTTPS_KEY_PATH + HTTPS_CERT_PATH, no con ambos.'); } if (!pfxPath && !(keyPath && certPath)) { throw new Error('Falta HTTPS_KEY_PATH o HTTPS_CERT_PATH: ambos son necesarios.'); } return { pfxPath, passphrase: vacio(process.env.HTTPS_PFX_PASSPHRASE), keyPath, certPath }; } /** WEB_DIST_DIR, o el build de Angular junto a la API (apps/web/dist/web/browser) si existe. */ function carpetaWeb(): string | null { const configurada = vacio(process.env.WEB_DIST_DIR); const ruta = configurada ? resolve(configurada) : resolve(import.meta.dirname, '../../../web/dist/web/browser'); if (existsSync(resolve(ruta, 'index.html'))) return ruta; if (configurada) throw new Error(`WEB_DIST_DIR no contiene un index.html: ${ruta}`); return null; } export default (): AppConfig => { const dbType = (process.env.DB_TYPE ?? 'HANA').toUpperCase(); if (dbType !== 'HANA' && dbType !== 'MSSQL') { throw new Error(`DB_TYPE inválido: ${dbType}. Valores permitidos: HANA, MSSQL.`); } const url = process.env.SL_URL; const companyDb = process.env.SL_COMPANY_DB; if (!url || !companyDb) { throw new Error('Faltan SL_URL y/o SL_COMPANY_DB en la configuración (.env).'); } return { port: Number(process.env.PORT ?? 3000), webOrigin: process.env.WEB_ORIGIN ?? 'http://localhost:4200', serviceLayer: { url: url.replace(/\/+$/, ''), companyDb, rejectUnauthorized: process.env.SL_REJECT_UNAUTHORIZED !== 'false', }, dbType, cookieSecure: process.env.COOKIE_SECURE === 'true', webDistDir: carpetaWeb(), https: leerHttps(), httpRedirectPort: Number(vacio(process.env.HTTP_REDIRECT_PORT)) || null, }; };