import 'package:em2rp/models/container_model.dart';
import 'package:em2rp/services/equipment_service.dart';

/// Générateur d'identifiants unifié pour l'application
/// Gère les équipements, containers et autres entités
class IdGenerator {
  // ============================================================================
  // ÉQUIPEMENTS
  // ============================================================================

  /// Génère un ID pour un équipement
  /// Format: {Marque4Chars}_{Modèle}_{#Numéro}
  /// Exemple: BEAM_7R_#1
  static String generateEquipmentId({
    required String brand,
    required String model,
    int? number,
  }) {
    final brandTrim = brand.trim().replaceAll(' ', '_');
    final modelTrim = model.trim().replaceAll(' ', '_');

    if (brandTrim.isEmpty && modelTrim.isEmpty) {
      return 'EQ-${DateTime.now().millisecondsSinceEpoch}${number != null ? '_$number' : ''}';
    }

    final brandPrefix = brandTrim.length >= 4
        ? brandTrim.substring(0, 4)
        : brandTrim;

    String baseId = modelTrim.isNotEmpty
        ? '${brandPrefix}_$modelTrim'
        : (brandPrefix.isNotEmpty ? brandPrefix : 'EQ');

    // Empêcher les ID commençant par BOX_ (réservé aux containers)
    if (baseId.toUpperCase().startsWith('BOX_')) {
      baseId = 'EQ_$baseId';
    }

    if (number != null) {
      baseId += '_#$number';
    }

    return baseId.toUpperCase();
  }

  /// Garantit l'unicité d'un ID d'équipement
  static Future<String> ensureUniqueEquipmentId(
    String baseId,
    EquipmentService service,
  ) async {
    // Vérifier que l'ID ne commence pas par BOX_
    if (baseId.toUpperCase().startsWith('BOX_')) {
      baseId = 'EQ_$baseId';
    }

    if (await service.isIdUnique(baseId)) {
      return baseId;
    }

    return '${baseId}_${DateTime.now().millisecondsSinceEpoch}';
  }

  // ============================================================================
  // CONTAINERS
  // ============================================================================

  /// Génère un ID pour un container
  /// Format: BOX_{Type}_{Nom}_{#Numéro}
  /// Exemple: BOX_FLIGHT_CASE_BEAM_#1
  static String generateContainerId({
    required ContainerType type,
    required String name,
    int? number,
  }) {
    final typeStr = containerTypeToString(type);
    final cleanName = _cleanId(name);

    if (number != null) {
      return 'BOX_${typeStr}_${cleanName}_#$number';
    }

    return 'BOX_${typeStr}_$cleanName';
  }

  /// Garantit l'unicité d'un ID de container
  /// Note: La vérification d'unicité doit être faite par l'appelant
  static String ensureUniqueContainerId(String baseId) {
    // Retourne simplement l'ID de base
    // L'unicité sera vérifiée au niveau du provider/form
    return baseId;
  }

  /// Génère un ID unique avec un timestamp si nécessaire
  static String generateUniqueContainerId(String baseId) {
    return '${baseId}_${DateTime.now().millisecondsSinceEpoch}';
  }


  // ============================================================================
  // UTILITAIRES
  // ============================================================================

  /// Nettoie une chaîne pour en faire un ID valide
  /// - Supprime les espaces (remplacés par _)
  /// - Supprime les caractères spéciaux
  /// - Met en majuscules
  static String _cleanId(String input) {
    return input
        .trim()
        .toUpperCase()
        .replaceAll(' ', '_')
        .replaceAll(RegExp(r'[^A-Z0-9_-]'), '');
  }

  /// Valide qu'un ID d'équipement ne commence pas par un préfixe réservé
  static String? validateEquipmentId(String id) {
    if (id.isEmpty) {
      return 'L\'identifiant ne peut pas être vide';
    }

    if (id.toUpperCase().startsWith('BOX_')) {
      return 'Les ID commençant par BOX_ sont réservés aux containers';
    }

    return null;
  }

  /// Valide qu'un ID de container commence bien par BOX_
  static String? validateContainerId(String id) {
    if (id.isEmpty) {
      return 'L\'identifiant ne peut pas être vide';
    }

    if (!id.toUpperCase().startsWith('BOX_')) {
      return 'Les containers doivent avoir un ID commençant par BOX_';
    }

    return null;
  }

  /// Détermine le type d'entité à partir d'un ID
  static EntityType getEntityType(String id) {
    if (id.toUpperCase().startsWith('BOX_')) {
      return EntityType.container;
    }
    return EntityType.equipment;
  }
}

/// Type d'entité identifiable
enum EntityType {
  equipment,
  container,
}

