/**
 * MongoDB Service
 * Handles TMS ID lookup from titles_data collection
 */

import { MongoClient, Db } from 'mongodb';
import { config } from '../config';
import { logger } from '../utils/logger';
import type { TitleData } from '../types';

class MongodbService {
  private static instance: MongodbService;
  private client: MongoClient | null = null;
  private db: Db | null = null;

  private constructor() {}

  public static getInstance(): MongodbService {
    if (!MongodbService.instance) {
      MongodbService.instance = new MongodbService();
    }
    return MongodbService.instance;
  }

  /**
   * Connect to MongoDB
   */
  public async connect(): Promise<void> {
    if (this.db) {
      logger.debug('MongoDB already connected');
      return;
    }

    try {
      logger.debug('Connecting to MongoDB...');
      this.client = new MongoClient(config.mongodbUri);
      await this.client.connect();
      this.db = this.client.db(config.mongodbDatabase);
      logger.debug('✅ MongoDB connected');
    } catch (error: any) {
      logger.error('MongoDB connection error', { error: error.message });
      throw error;
    }
  }

  /**
   * Get TMS ID from MongoDB titles_data collection
   * @param geId - GE ID (e.g., "1000")
   * @param lang - Language code (e.g., "de", "us")
   * @returns TMS ID (e.g., "12345")
   */
  public async getTmsId(geId: string, lang: string): Promise<string> {
    if (!this.db) {
      throw new Error('MongoDB not connected');
    }

    try {
      // Convert inputs to match MongoDB data format (uppercase lang)
      const geIdSearch = geId.trim();
      const langSearch = lang.trim().toUpperCase();
      
      logger.debug('Looking up TMS ID', { geId: geIdSearch, lang: langSearch });

      const collection = this.db.collection<TitleData>('titles_data');
      
      // Query by geId and lang (lang must be uppercase)
      const doc = await collection.findOne({
        geId: geIdSearch,
        lang: langSearch,
      });

      if (!doc) {
        throw new Error(`TMS data not found for GE ${geIdSearch} ${langSearch}`);
      }

      // Extract TMS ID from trTmsLink or tmsId field (priority: trTmsLink > tmsId)
      let tmsId: string | undefined;

      if (doc.trTmsLink) {
        // Extract ID from URL like "https://tms.kiledel.com/project/12345"
        const match = doc.trTmsLink.match(/\/project\/(\d+)/);
        if (match) {
          tmsId = match[1];
          logger.debug('TMS ID extracted from trTmsLink', { tmsId });
        }
      }

      if (!tmsId && doc.tmsId) {
        tmsId = doc.tmsId.toString().trim();
        logger.debug('TMS ID from direct field', { tmsId });
      }

      if (!tmsId) {
        throw new Error(`TMS ID chưa được bổ sung cho GE ${geIdSearch} ${langSearch}`);
      }

      logger.debug('Found TMS ID', { geId: geIdSearch, lang: langSearch, tmsId });
      return tmsId;
    } catch (error: any) {
      logger.error('Error getting TMS ID', {
        geId,
        lang,
        error: error.message,
      });
      throw error;
    }
  }

  /**
   * Get TMS URL for a GE/lang combination
   */
  public async getTmsUrl(geId: string, lang: string): Promise<string> {
    const tmsId = await this.getTmsId(geId, lang);
    return `https://tms.kiledel.com/project/${tmsId}`;
  }

  /**
   * Close MongoDB connection
   */
  public async close(): Promise<void> {
    if (this.client) {
      await this.client.close();
      this.client = null;
      this.db = null;
      logger.debug('MongoDB connection closed');
    }
  }
}

export const mongodbService = MongodbService.getInstance();
