/// Implémentation du repository de messagerie v4
library messaging_repository_impl;

import 'package:injectable/injectable.dart';

import '../../../../core/error/exceptions.dart';
import '../../domain/entities/conversation.dart';
import '../../domain/entities/message.dart';
import '../../domain/entities/contact_policy.dart';
import '../../domain/repositories/messaging_repository.dart';
import '../datasources/messaging_remote_datasource.dart';

@LazySingleton(as: MessagingRepository)
class MessagingRepositoryImpl implements MessagingRepository {
  final MessagingRemoteDatasource remoteDatasource;

  MessagingRepositoryImpl({required this.remoteDatasource});

  @override
  Future<List<ConversationSummary>> getMesConversations() async {
    try {
      return await remoteDatasource.getMesConversations();
    } on UnauthorizedException {
      throw Exception('Session expirée — veuillez vous reconnecter');
    } on ServerException catch (e) {
      throw Exception(e.message);
    } catch (e) {
      throw Exception('Erreur inattendue: $e');
    }
  }

  @override
  Future<Conversation> getConversation(String conversationId) async {
    try {
      return await remoteDatasource.getConversation(conversationId);
    } on NotFoundException {
      throw Exception('Conversation non trouvée');
    } on UnauthorizedException {
      throw Exception('Session expirée — veuillez vous reconnecter');
    } on ServerException catch (e) {
      throw Exception(e.message);
    } catch (e) {
      throw Exception('Erreur inattendue: $e');
    }
  }

  @override
  Future<Conversation> demarrerConversationDirecte({
    required String destinataireId,
    required String organisationId,
    String? premierMessage,
  }) async {
    try {
      return await remoteDatasource.demarrerConversationDirecte(
        destinataireId: destinataireId,
        organisationId: organisationId,
        premierMessage: premierMessage,
      );
    } on UnauthorizedException {
      throw Exception('Session expirée — veuillez vous reconnecter');
    } on ServerException catch (e) {
      throw Exception(e.message);
    } catch (e) {
      throw Exception('Erreur inattendue: $e');
    }
  }

  @override
  Future<Conversation> demarrerConversationRole({
    required String roleCible,
    required String organisationId,
    String? premierMessage,
  }) async {
    try {
      return await remoteDatasource.demarrerConversationRole(
        roleCible: roleCible,
        organisationId: organisationId,
        premierMessage: premierMessage,
      );
    } on UnauthorizedException {
      throw Exception('Session expirée — veuillez vous reconnecter');
    } on ServerException catch (e) {
      throw Exception(e.message);
    } catch (e) {
      throw Exception('Erreur inattendue: $e');
    }
  }

  @override
  Future<void> archiverConversation(String conversationId) async {
    try {
      await remoteDatasource.archiverConversation(conversationId);
    } on UnauthorizedException {
      throw Exception('Session expirée — veuillez vous reconnecter');
    } on ServerException catch (e) {
      throw Exception(e.message);
    } catch (e) {
      throw Exception('Erreur inattendue: $e');
    }
  }

  @override
  Future<Message> envoyerMessage(
    String conversationId, {
    required String typeMessage,
    String? contenu,
    String? urlFichier,
    int? dureeAudio,
    String? messageParentId,
  }) async {
    try {
      return await remoteDatasource.envoyerMessage(
        conversationId,
        typeMessage: typeMessage,
        contenu: contenu,
        urlFichier: urlFichier,
        dureeAudio: dureeAudio,
        messageParentId: messageParentId,
      );
    } on UnauthorizedException {
      throw Exception('Session expirée — veuillez vous reconnecter');
    } on ForbiddenException catch (e) {
      throw Exception(e.message);
    } on ServerException catch (e) {
      throw Exception(e.message);
    } catch (e) {
      throw Exception('Erreur inattendue: $e');
    }
  }

  @override
  Future<List<Message>> getMessages(String conversationId, {int page = 0}) async {
    try {
      return await remoteDatasource.getMessages(conversationId, page: page);
    } on UnauthorizedException {
      throw Exception('Session expirée — veuillez vous reconnecter');
    } on ServerException catch (e) {
      throw Exception(e.message);
    } catch (e) {
      throw Exception('Erreur inattendue: $e');
    }
  }

  @override
  Future<void> marquerLu(String conversationId) async {
    try {
      await remoteDatasource.marquerLu(conversationId);
    } catch (_) {
      // Non-bloquant — ignorer les erreurs de marquage
    }
  }

  @override
  Future<void> supprimerMessage(String conversationId, String messageId) async {
    try {
      await remoteDatasource.supprimerMessage(conversationId, messageId);
    } on UnauthorizedException {
      throw Exception('Session expirée — veuillez vous reconnecter');
    } on ServerException catch (e) {
      throw Exception(e.message);
    } catch (e) {
      throw Exception('Erreur inattendue: $e');
    }
  }

  @override
  Future<void> bloquerMembre({
    required String membreABloquerId,
    String? organisationId,
    String? raison,
  }) async {
    try {
      await remoteDatasource.bloquerMembre(
        membreABloquerId: membreABloquerId,
        organisationId: organisationId,
        raison: raison,
      );
    } on UnauthorizedException {
      throw Exception('Session expirée — veuillez vous reconnecter');
    } on ServerException catch (e) {
      throw Exception(e.message);
    } catch (e) {
      throw Exception('Erreur inattendue: $e');
    }
  }

  @override
  Future<void> debloquerMembre(String membreId, {String? organisationId}) async {
    try {
      await remoteDatasource.debloquerMembre(membreId, organisationId: organisationId);
    } on UnauthorizedException {
      throw Exception('Session expirée — veuillez vous reconnecter');
    } on ServerException catch (e) {
      throw Exception(e.message);
    } catch (e) {
      throw Exception('Erreur inattendue: $e');
    }
  }

  @override
  Future<List<Map<String, dynamic>>> getMesBlocages() async {
    try {
      return await remoteDatasource.getMesBlocages();
    } on UnauthorizedException {
      throw Exception('Session expirée — veuillez vous reconnecter');
    } on ServerException catch (e) {
      throw Exception(e.message);
    } catch (e) {
      throw Exception('Erreur inattendue: $e');
    }
  }

  @override
  Future<ContactPolicy> getPolitique(String organisationId) async {
    try {
      return await remoteDatasource.getPolitique(organisationId);
    } on UnauthorizedException {
      throw Exception('Session expirée — veuillez vous reconnecter');
    } on ServerException catch (e) {
      throw Exception(e.message);
    } catch (e) {
      throw Exception('Erreur inattendue: $e');
    }
  }

  @override
  Future<ContactPolicy> mettreAJourPolitique(
    String organisationId, {
    required String typePolitique,
    required bool autoriserMembreVersMembre,
    required bool autoriserMembreVersRole,
    required bool autoriserNotesVocales,
  }) async {
    try {
      return await remoteDatasource.mettreAJourPolitique(
        organisationId,
        typePolitique: typePolitique,
        autoriserMembreVersMembre: autoriserMembreVersMembre,
        autoriserMembreVersRole: autoriserMembreVersRole,
        autoriserNotesVocales: autoriserNotesVocales,
      );
    } on UnauthorizedException {
      throw Exception('Session expirée — veuillez vous reconnecter');
    } on ForbiddenException catch (e) {
      throw Exception(e.message);
    } on ServerException catch (e) {
      throw Exception(e.message);
    } catch (e) {
      throw Exception('Erreur inattendue: $e');
    }
  }
}
