/**
 * ╔═══════════════════════════════════════════════════════════════╗
 * ║  ИНФУД v6.4 NestJS — Точка входа (main.ts)                   ║
 * ║  Шаг 1: Стабильный пилот                                      ║
 * ╚═══════════════════════════════════════════════════════════════╝
 *
 * Задачи этого файла:
 *  1. Создать NestJS-приложение с платформой Express
 *  2. Настроить глобальные pipes, filters, interceptors
 *  3. Раздавать статику (фронтенд infud_v6.4.html)
 *  4. Подключить WebSocket-адаптер (совместимость с фронтендом)
 *  5. Вывести баннер при старте
 */

import 'reflect-metadata';
import { NestFactory, HttpAdapterHost } from '@nestjs/core';
import { ValidationPipe, Logger }       from '@nestjs/common';
import { WsAdapter }                    from '@nestjs/platform-ws';
import * as path                        from 'path';

import { AppModule }             from './app.module';
import { HttpExceptionFilter }   from './common/filters/http-exception.filter';
import { TransformInterceptor }  from './common/interceptors/transform.interceptor';

async function bootstrap(): Promise<void> {
  const logger = new Logger('Bootstrap');

  /* ── 1. Создаём приложение ── */
  const app = await NestFactory.create(AppModule, {
    logger: ['log', 'warn', 'error'],
    // CORS разрешён для всех в режиме пилота.
    // В production включить STRICT_CORS через feature flag.
    cors: {
      origin:      (_origin: string | undefined, cb: Function) => cb(null, true),
      credentials: true,
      methods:     'GET,HEAD,PUT,PATCH,POST,DELETE,OPTIONS',
    },
  });

  /* ── 2. WebSocket адаптер (стандартный ws, НЕ socket.io) ──
   * Фронтенд подключается через: ws://host:3000/?token=<JWT>
   * Это ОБЯЗАТЕЛЬНО для совместимости с infud_v6.4.html
   */
  app.useWebSocketAdapter(new WsAdapter(app));

  /* ── 3. Глобальная валидация DTO ──
   * transform: true  → автоматически конвертирует типы (@Type)
   * whitelist: true  → игнорирует лишние поля в теле запроса
   * forbidNonWhitelisted: false → не бросает ошибку на лишние поля
   *   (нужно для обратной совместимости с фронтендом)
   */
  app.useGlobalPipes(
    new ValidationPipe({
      transform:             true,
      whitelist:             true,
      forbidNonWhitelisted:  false,
      transformOptions:      { enableImplicitConversion: true },
    }),
  );

  /* ── 4. Глобальный фильтр ошибок ──
   * Формирует единый формат: { statusCode, error, path, ts }
   * Фронтенд ожидает поле "error" при HTTP >= 400
   */
  const { httpAdapter } = app.get(HttpAdapterHost);
  app.useGlobalFilters(new HttpExceptionFilter(httpAdapter));

  /* ── 5. Глобальный transform-interceptor ──
   * НЕ оборачивает ответы в { data: ... }.
   * Возвращает JSON 1:1 как в старом Express-бэкенде.
   */
  app.useGlobalInterceptors(new TransformInterceptor());

  /* ── 6. Статика (фронтенд) ──
   * Отдаём infud_v6.4.html, manifest.json, etc.
   * из корневой папки проекта (рядом с package.json)
   */
  const expressApp = app.getHttpAdapter().getInstance();
  const serveStatic = require('express').static;
  expressApp.use(serveStatic(path.resolve(process.cwd()), { maxAge: 0 }));

  /* ── 7. Опциональный gzip ── */
  try {
    const compression = require('compression');
    expressApp.use(compression());
  } catch (_) { /* compression не установлен — пропускаем */ }

  /* ── 8. Запуск ── */
  const port = parseInt(process.env.PORT ?? '3000', 10);
  await app.listen(port, '0.0.0.0');

  const sep = '═'.repeat(60);
  logger.log('\n' + sep);
  logger.log(`  ИНФУД v6.4 NestJS — Шаг 1 (Стабильный пилот)`);
  logger.log(`  URL:      http://localhost:${port}`);
  logger.log(`  Frontend: http://localhost:${port}/infud_v6.4.html`);
  logger.log(`  Env:      ${process.env.NODE_ENV ?? 'development'}`);
  logger.log(sep);
}

bootstrap().catch(err => {
  console.error('[FATAL] Ошибка запуска:', err);
  process.exit(1);
});
