Clean project: remove test files, debug logs, and add documentation

This commit is contained in:
dahoud
2025-10-05 13:41:33 +00:00
parent 96a17eadbd
commit 291847924c
438 changed files with 65754 additions and 32713 deletions

View File

@@ -0,0 +1,597 @@
/// BLoC pour la gestion des cotisations
library cotisations_bloc;
import 'package:flutter_bloc/flutter_bloc.dart';
import '../../../core/utils/logger.dart';
import '../data/models/cotisation_model.dart';
import 'cotisations_event.dart';
import 'cotisations_state.dart';
/// BLoC pour gérer l'état des cotisations
class CotisationsBloc extends Bloc<CotisationsEvent, CotisationsState> {
CotisationsBloc() : super(const CotisationsInitial()) {
on<LoadCotisations>(_onLoadCotisations);
on<LoadCotisationById>(_onLoadCotisationById);
on<CreateCotisation>(_onCreateCotisation);
on<UpdateCotisation>(_onUpdateCotisation);
on<DeleteCotisation>(_onDeleteCotisation);
on<SearchCotisations>(_onSearchCotisations);
on<LoadCotisationsByMembre>(_onLoadCotisationsByMembre);
on<LoadCotisationsPayees>(_onLoadCotisationsPayees);
on<LoadCotisationsNonPayees>(_onLoadCotisationsNonPayees);
on<LoadCotisationsEnRetard>(_onLoadCotisationsEnRetard);
on<EnregistrerPaiement>(_onEnregistrerPaiement);
on<LoadCotisationsStats>(_onLoadCotisationsStats);
on<GenererCotisationsAnnuelles>(_onGenererCotisationsAnnuelles);
on<EnvoyerRappelPaiement>(_onEnvoyerRappelPaiement);
}
/// Charger la liste des cotisations
Future<void> _onLoadCotisations(
LoadCotisations event,
Emitter<CotisationsState> emit,
) async {
try {
AppLogger.blocEvent('CotisationsBloc', 'LoadCotisations', data: {
'page': event.page,
'size': event.size,
});
emit(const CotisationsLoading(message: 'Chargement des cotisations...'));
// Simuler un délai réseau
await Future.delayed(const Duration(milliseconds: 500));
// Données mock
final cotisations = _getMockCotisations();
final total = cotisations.length;
final totalPages = (total / event.size).ceil();
// Pagination
final start = event.page * event.size;
final end = (start + event.size).clamp(0, total);
final paginatedCotisations = cotisations.sublist(
start.clamp(0, total),
end,
);
emit(CotisationsLoaded(
cotisations: paginatedCotisations,
total: total,
page: event.page,
size: event.size,
totalPages: totalPages,
));
AppLogger.blocState('CotisationsBloc', 'CotisationsLoaded', data: {
'count': paginatedCotisations.length,
'total': total,
});
} catch (e, stackTrace) {
AppLogger.error(
'Erreur lors du chargement des cotisations',
error: e,
stackTrace: stackTrace,
);
emit(CotisationsError(
message: 'Erreur lors du chargement des cotisations',
error: e,
));
}
}
/// Charger une cotisation par ID
Future<void> _onLoadCotisationById(
LoadCotisationById event,
Emitter<CotisationsState> emit,
) async {
try {
AppLogger.blocEvent('CotisationsBloc', 'LoadCotisationById', data: {
'id': event.id,
});
emit(const CotisationsLoading(message: 'Chargement de la cotisation...'));
await Future.delayed(const Duration(milliseconds: 300));
final cotisations = _getMockCotisations();
final cotisation = cotisations.firstWhere(
(c) => c.id == event.id,
orElse: () => throw Exception('Cotisation non trouvée'),
);
emit(CotisationDetailLoaded(cotisation: cotisation));
AppLogger.blocState('CotisationsBloc', 'CotisationDetailLoaded');
} catch (e, stackTrace) {
AppLogger.error(
'Erreur lors du chargement de la cotisation',
error: e,
stackTrace: stackTrace,
);
emit(CotisationsError(
message: 'Cotisation non trouvée',
error: e,
));
}
}
/// Créer une nouvelle cotisation
Future<void> _onCreateCotisation(
CreateCotisation event,
Emitter<CotisationsState> emit,
) async {
try {
AppLogger.blocEvent('CotisationsBloc', 'CreateCotisation');
emit(const CotisationsLoading(message: 'Création de la cotisation...'));
await Future.delayed(const Duration(milliseconds: 500));
final newCotisation = event.cotisation.copyWith(
id: 'cot_${DateTime.now().millisecondsSinceEpoch}',
dateCreation: DateTime.now(),
);
emit(CotisationCreated(cotisation: newCotisation));
AppLogger.blocState('CotisationsBloc', 'CotisationCreated');
} catch (e, stackTrace) {
AppLogger.error(
'Erreur lors de la création de la cotisation',
error: e,
stackTrace: stackTrace,
);
emit(CotisationsError(
message: 'Erreur lors de la création de la cotisation',
error: e,
));
}
}
/// Mettre à jour une cotisation
Future<void> _onUpdateCotisation(
UpdateCotisation event,
Emitter<CotisationsState> emit,
) async {
try {
AppLogger.blocEvent('CotisationsBloc', 'UpdateCotisation', data: {
'id': event.id,
});
emit(const CotisationsLoading(message: 'Mise à jour de la cotisation...'));
await Future.delayed(const Duration(milliseconds: 500));
final updatedCotisation = event.cotisation.copyWith(
id: event.id,
dateModification: DateTime.now(),
);
emit(CotisationUpdated(cotisation: updatedCotisation));
AppLogger.blocState('CotisationsBloc', 'CotisationUpdated');
} catch (e, stackTrace) {
AppLogger.error(
'Erreur lors de la mise à jour de la cotisation',
error: e,
stackTrace: stackTrace,
);
emit(CotisationsError(
message: 'Erreur lors de la mise à jour de la cotisation',
error: e,
));
}
}
/// Supprimer une cotisation
Future<void> _onDeleteCotisation(
DeleteCotisation event,
Emitter<CotisationsState> emit,
) async {
try {
AppLogger.blocEvent('CotisationsBloc', 'DeleteCotisation', data: {
'id': event.id,
});
emit(const CotisationsLoading(message: 'Suppression de la cotisation...'));
await Future.delayed(const Duration(milliseconds: 500));
emit(CotisationDeleted(id: event.id));
AppLogger.blocState('CotisationsBloc', 'CotisationDeleted');
} catch (e, stackTrace) {
AppLogger.error(
'Erreur lors de la suppression de la cotisation',
error: e,
stackTrace: stackTrace,
);
emit(CotisationsError(
message: 'Erreur lors de la suppression de la cotisation',
error: e,
));
}
}
/// Rechercher des cotisations
Future<void> _onSearchCotisations(
SearchCotisations event,
Emitter<CotisationsState> emit,
) async {
try {
AppLogger.blocEvent('CotisationsBloc', 'SearchCotisations');
emit(const CotisationsLoading(message: 'Recherche en cours...'));
await Future.delayed(const Duration(milliseconds: 500));
var cotisations = _getMockCotisations();
// Filtrer par membre
if (event.membreId != null) {
cotisations = cotisations
.where((c) => c.membreId == event.membreId)
.toList();
}
// Filtrer par statut
if (event.statut != null) {
cotisations = cotisations
.where((c) => c.statut == event.statut)
.toList();
}
// Filtrer par type
if (event.type != null) {
cotisations = cotisations
.where((c) => c.type == event.type)
.toList();
}
// Filtrer par année
if (event.annee != null) {
cotisations = cotisations
.where((c) => c.annee == event.annee)
.toList();
}
final total = cotisations.length;
final totalPages = (total / event.size).ceil();
// Pagination
final start = event.page * event.size;
final end = (start + event.size).clamp(0, total);
final paginatedCotisations = cotisations.sublist(
start.clamp(0, total),
end,
);
emit(CotisationsLoaded(
cotisations: paginatedCotisations,
total: total,
page: event.page,
size: event.size,
totalPages: totalPages,
));
AppLogger.blocState('CotisationsBloc', 'CotisationsLoaded (search)');
} catch (e, stackTrace) {
AppLogger.error(
'Erreur lors de la recherche de cotisations',
error: e,
stackTrace: stackTrace,
);
emit(CotisationsError(
message: 'Erreur lors de la recherche',
error: e,
));
}
}
/// Charger les cotisations d'un membre
Future<void> _onLoadCotisationsByMembre(
LoadCotisationsByMembre event,
Emitter<CotisationsState> emit,
) async {
try {
AppLogger.blocEvent('CotisationsBloc', 'LoadCotisationsByMembre', data: {
'membreId': event.membreId,
});
emit(const CotisationsLoading(message: 'Chargement des cotisations du membre...'));
await Future.delayed(const Duration(milliseconds: 500));
final cotisations = _getMockCotisations()
.where((c) => c.membreId == event.membreId)
.toList();
final total = cotisations.length;
final totalPages = (total / event.size).ceil();
emit(CotisationsLoaded(
cotisations: cotisations,
total: total,
page: event.page,
size: event.size,
totalPages: totalPages,
));
AppLogger.blocState('CotisationsBloc', 'CotisationsLoaded (by membre)');
} catch (e, stackTrace) {
AppLogger.error(
'Erreur lors du chargement des cotisations du membre',
error: e,
stackTrace: stackTrace,
);
emit(CotisationsError(
message: 'Erreur lors du chargement',
error: e,
));
}
}
/// Charger les cotisations payées
Future<void> _onLoadCotisationsPayees(
LoadCotisationsPayees event,
Emitter<CotisationsState> emit,
) async {
try {
emit(const CotisationsLoading(message: 'Chargement des cotisations payées...'));
await Future.delayed(const Duration(milliseconds: 500));
final cotisations = _getMockCotisations()
.where((c) => c.statut == StatutCotisation.payee)
.toList();
final total = cotisations.length;
final totalPages = (total / event.size).ceil();
emit(CotisationsLoaded(
cotisations: cotisations,
total: total,
page: event.page,
size: event.size,
totalPages: totalPages,
));
} catch (e, stackTrace) {
AppLogger.error('Erreur', error: e, stackTrace: stackTrace);
emit(CotisationsError(message: 'Erreur', error: e));
}
}
/// Charger les cotisations non payées
Future<void> _onLoadCotisationsNonPayees(
LoadCotisationsNonPayees event,
Emitter<CotisationsState> emit,
) async {
try {
emit(const CotisationsLoading(message: 'Chargement des cotisations non payées...'));
await Future.delayed(const Duration(milliseconds: 500));
final cotisations = _getMockCotisations()
.where((c) => c.statut == StatutCotisation.nonPayee)
.toList();
final total = cotisations.length;
final totalPages = (total / event.size).ceil();
emit(CotisationsLoaded(
cotisations: cotisations,
total: total,
page: event.page,
size: event.size,
totalPages: totalPages,
));
} catch (e, stackTrace) {
AppLogger.error('Erreur', error: e, stackTrace: stackTrace);
emit(CotisationsError(message: 'Erreur', error: e));
}
}
/// Charger les cotisations en retard
Future<void> _onLoadCotisationsEnRetard(
LoadCotisationsEnRetard event,
Emitter<CotisationsState> emit,
) async {
try {
emit(const CotisationsLoading(message: 'Chargement des cotisations en retard...'));
await Future.delayed(const Duration(milliseconds: 500));
final cotisations = _getMockCotisations()
.where((c) => c.statut == StatutCotisation.enRetard)
.toList();
final total = cotisations.length;
final totalPages = (total / event.size).ceil();
emit(CotisationsLoaded(
cotisations: cotisations,
total: total,
page: event.page,
size: event.size,
totalPages: totalPages,
));
} catch (e, stackTrace) {
AppLogger.error('Erreur', error: e, stackTrace: stackTrace);
emit(CotisationsError(message: 'Erreur', error: e));
}
}
/// Enregistrer un paiement
Future<void> _onEnregistrerPaiement(
EnregistrerPaiement event,
Emitter<CotisationsState> emit,
) async {
try {
AppLogger.blocEvent('CotisationsBloc', 'EnregistrerPaiement');
emit(const CotisationsLoading(message: 'Enregistrement du paiement...'));
await Future.delayed(const Duration(milliseconds: 500));
final cotisations = _getMockCotisations();
final cotisation = cotisations.firstWhere((c) => c.id == event.cotisationId);
final updatedCotisation = cotisation.copyWith(
montantPaye: event.montant,
datePaiement: event.datePaiement,
methodePaiement: event.methodePaiement,
numeroPaiement: event.numeroPaiement,
referencePaiement: event.referencePaiement,
statut: event.montant >= cotisation.montant
? StatutCotisation.payee
: StatutCotisation.partielle,
dateModification: DateTime.now(),
);
emit(PaiementEnregistre(cotisation: updatedCotisation));
AppLogger.blocState('CotisationsBloc', 'PaiementEnregistre');
} catch (e, stackTrace) {
AppLogger.error('Erreur', error: e, stackTrace: stackTrace);
emit(CotisationsError(message: 'Erreur lors de l\'enregistrement du paiement', error: e));
}
}
/// Charger les statistiques
Future<void> _onLoadCotisationsStats(
LoadCotisationsStats event,
Emitter<CotisationsState> emit,
) async {
try {
emit(const CotisationsLoading(message: 'Chargement des statistiques...'));
await Future.delayed(const Duration(milliseconds: 500));
final cotisations = _getMockCotisations();
final stats = {
'total': cotisations.length,
'payees': cotisations.where((c) => c.statut == StatutCotisation.payee).length,
'nonPayees': cotisations.where((c) => c.statut == StatutCotisation.nonPayee).length,
'enRetard': cotisations.where((c) => c.statut == StatutCotisation.enRetard).length,
'partielles': cotisations.where((c) => c.statut == StatutCotisation.partielle).length,
'montantTotal': cotisations.fold<double>(0, (sum, c) => sum + c.montant),
'montantPaye': cotisations.fold<double>(0, (sum, c) => sum + (c.montantPaye ?? 0)),
'montantRestant': cotisations.fold<double>(0, (sum, c) => sum + c.montantRestant),
'tauxRecouvrement': 0.0,
};
if (stats['montantTotal']! > 0) {
stats['tauxRecouvrement'] = (stats['montantPaye']! / stats['montantTotal']!) * 100;
}
emit(CotisationsStatsLoaded(stats: stats));
} catch (e, stackTrace) {
AppLogger.error('Erreur', error: e, stackTrace: stackTrace);
emit(CotisationsError(message: 'Erreur', error: e));
}
}
/// Générer les cotisations annuelles
Future<void> _onGenererCotisationsAnnuelles(
GenererCotisationsAnnuelles event,
Emitter<CotisationsState> emit,
) async {
try {
emit(const CotisationsLoading(message: 'Génération des cotisations...'));
await Future.delayed(const Duration(seconds: 1));
// Simuler la génération de 50 cotisations
emit(const CotisationsGenerees(nombreGenere: 50));
} catch (e, stackTrace) {
AppLogger.error('Erreur', error: e, stackTrace: stackTrace);
emit(CotisationsError(message: 'Erreur', error: e));
}
}
/// Envoyer un rappel de paiement
Future<void> _onEnvoyerRappelPaiement(
EnvoyerRappelPaiement event,
Emitter<CotisationsState> emit,
) async {
try {
emit(const CotisationsLoading(message: 'Envoi du rappel...'));
await Future.delayed(const Duration(milliseconds: 500));
emit(RappelEnvoye(cotisationId: event.cotisationId));
} catch (e, stackTrace) {
AppLogger.error('Erreur', error: e, stackTrace: stackTrace);
emit(CotisationsError(message: 'Erreur', error: e));
}
}
/// Données mock pour les tests
List<CotisationModel> _getMockCotisations() {
final now = DateTime.now();
return [
CotisationModel(
id: 'cot_001',
membreId: 'mbr_001',
membreNom: 'Dupont',
membrePrenom: 'Jean',
montant: 50000,
dateEcheance: DateTime(now.year, 12, 31),
annee: now.year,
statut: StatutCotisation.payee,
montantPaye: 50000,
datePaiement: DateTime(now.year, 1, 15),
methodePaiement: MethodePaiement.virement,
),
CotisationModel(
id: 'cot_002',
membreId: 'mbr_002',
membreNom: 'Martin',
membrePrenom: 'Marie',
montant: 50000,
dateEcheance: DateTime(now.year, 12, 31),
annee: now.year,
statut: StatutCotisation.nonPayee,
),
CotisationModel(
id: 'cot_003',
membreId: 'mbr_003',
membreNom: 'Bernard',
membrePrenom: 'Pierre',
montant: 50000,
dateEcheance: DateTime(now.year - 1, 12, 31),
annee: now.year - 1,
statut: StatutCotisation.enRetard,
),
CotisationModel(
id: 'cot_004',
membreId: 'mbr_004',
membreNom: 'Dubois',
membrePrenom: 'Sophie',
montant: 50000,
dateEcheance: DateTime(now.year, 12, 31),
annee: now.year,
statut: StatutCotisation.partielle,
montantPaye: 25000,
datePaiement: DateTime(now.year, 2, 10),
methodePaiement: MethodePaiement.especes,
),
CotisationModel(
id: 'cot_005',
membreId: 'mbr_005',
membreNom: 'Petit',
membrePrenom: 'Luc',
montant: 50000,
dateEcheance: DateTime(now.year, 12, 31),
annee: now.year,
statut: StatutCotisation.payee,
montantPaye: 50000,
datePaiement: DateTime(now.year, 3, 5),
methodePaiement: MethodePaiement.mobileMoney,
),
];
}
}