248 lines
8.4 KiB
Dart
248 lines
8.4 KiB
Dart
import 'package:cloud_firestore/cloud_firestore.dart';
|
|
import 'package:em2rp/models/event_model.dart';
|
|
import 'package:em2rp/models/equipment_model.dart';
|
|
import 'package:em2rp/services/equipment_status_calculator.dart';
|
|
|
|
/// Service étendu pour gérer les 4 étapes : Préparation, Chargement, Déchargement, Retour
|
|
class EventPreparationServiceExtended {
|
|
final FirebaseFirestore _firestore = FirebaseFirestore.instance;
|
|
|
|
CollectionReference get _eventsCollection => _firestore.collection('events');
|
|
CollectionReference get _equipmentCollection => _firestore.collection('equipments');
|
|
|
|
// === CHARGEMENT (LOADING) ===
|
|
|
|
/// Valider un équipement individuel pour le chargement
|
|
Future<void> validateEquipmentLoading(String eventId, String equipmentId) async {
|
|
try {
|
|
final event = await _getEvent(eventId);
|
|
if (event == null) throw Exception('Event not found');
|
|
|
|
final updatedEquipment = event.assignedEquipment.map((eq) {
|
|
if (eq.equipmentId == equipmentId) {
|
|
return eq.copyWith(isLoaded: true);
|
|
}
|
|
return eq;
|
|
}).toList();
|
|
|
|
// Vérifier si tous les équipements sont chargés
|
|
final allLoaded = updatedEquipment.every((eq) => eq.isLoaded);
|
|
|
|
final updateData = <String, dynamic>{
|
|
'assignedEquipment': updatedEquipment.map((e) => e.toMap()).toList(),
|
|
};
|
|
|
|
// Si tous sont chargés, mettre à jour le statut
|
|
if (allLoaded) {
|
|
updateData['loadingStatus'] = loadingStatusToString(LoadingStatus.completed);
|
|
} else {
|
|
updateData['loadingStatus'] = loadingStatusToString(LoadingStatus.inProgress);
|
|
}
|
|
|
|
await _eventsCollection.doc(eventId).update(updateData);
|
|
} catch (e) {
|
|
print('Error validating equipment loading: $e');
|
|
rethrow;
|
|
}
|
|
}
|
|
|
|
/// Valider tous les équipements pour le chargement
|
|
Future<void> validateAllLoading(String eventId) async {
|
|
try {
|
|
final event = await _getEvent(eventId);
|
|
if (event == null) throw Exception('Event not found');
|
|
|
|
final updatedEquipment = event.assignedEquipment.map((eq) {
|
|
return eq.copyWith(isLoaded: true);
|
|
}).toList();
|
|
|
|
await _eventsCollection.doc(eventId).update({
|
|
'assignedEquipment': updatedEquipment.map((e) => e.toMap()).toList(),
|
|
'loadingStatus': loadingStatusToString(LoadingStatus.completed),
|
|
});
|
|
|
|
// Invalider le cache des statuts d'équipement
|
|
EquipmentStatusCalculator.invalidateGlobalCache();
|
|
} catch (e) {
|
|
print('Error validating all loading: $e');
|
|
rethrow;
|
|
}
|
|
}
|
|
|
|
// === DÉCHARGEMENT (UNLOADING) ===
|
|
|
|
/// Valider un équipement individuel pour le déchargement
|
|
Future<void> validateEquipmentUnloading(String eventId, String equipmentId) async {
|
|
try {
|
|
final event = await _getEvent(eventId);
|
|
if (event == null) throw Exception('Event not found');
|
|
|
|
final updatedEquipment = event.assignedEquipment.map((eq) {
|
|
if (eq.equipmentId == equipmentId) {
|
|
return eq.copyWith(isUnloaded: true);
|
|
}
|
|
return eq;
|
|
}).toList();
|
|
|
|
// Vérifier si tous les équipements sont déchargés
|
|
final allUnloaded = updatedEquipment.every((eq) => eq.isUnloaded);
|
|
|
|
final updateData = <String, dynamic>{
|
|
'assignedEquipment': updatedEquipment.map((e) => e.toMap()).toList(),
|
|
};
|
|
|
|
// Si tous sont déchargés, mettre à jour le statut
|
|
if (allUnloaded) {
|
|
updateData['unloadingStatus'] = unloadingStatusToString(UnloadingStatus.completed);
|
|
} else {
|
|
updateData['unloadingStatus'] = unloadingStatusToString(UnloadingStatus.inProgress);
|
|
}
|
|
|
|
await _eventsCollection.doc(eventId).update(updateData);
|
|
} catch (e) {
|
|
print('Error validating equipment unloading: $e');
|
|
rethrow;
|
|
}
|
|
}
|
|
|
|
/// Valider tous les équipements pour le déchargement
|
|
Future<void> validateAllUnloading(String eventId) async {
|
|
try {
|
|
final event = await _getEvent(eventId);
|
|
if (event == null) throw Exception('Event not found');
|
|
|
|
final updatedEquipment = event.assignedEquipment.map((eq) {
|
|
return eq.copyWith(isUnloaded: true);
|
|
}).toList();
|
|
|
|
await _eventsCollection.doc(eventId).update({
|
|
'assignedEquipment': updatedEquipment.map((e) => e.toMap()).toList(),
|
|
'unloadingStatus': unloadingStatusToString(UnloadingStatus.completed),
|
|
});
|
|
|
|
// Invalider le cache des statuts d'équipement
|
|
EquipmentStatusCalculator.invalidateGlobalCache();
|
|
} catch (e) {
|
|
print('Error validating all unloading: $e');
|
|
rethrow;
|
|
}
|
|
}
|
|
|
|
// === PRÉPARATION + CHARGEMENT ===
|
|
|
|
/// Valider préparation ET chargement en même temps
|
|
Future<void> validateAllPreparationAndLoading(String eventId) async {
|
|
try {
|
|
final event = await _getEvent(eventId);
|
|
if (event == null) throw Exception('Event not found');
|
|
|
|
final updatedEquipment = event.assignedEquipment.map((eq) {
|
|
return eq.copyWith(isPrepared: true, isLoaded: true);
|
|
}).toList();
|
|
|
|
await _eventsCollection.doc(eventId).update({
|
|
'assignedEquipment': updatedEquipment.map((e) => e.toMap()).toList(),
|
|
'preparationStatus': preparationStatusToString(PreparationStatus.completed),
|
|
'loadingStatus': loadingStatusToString(LoadingStatus.completed),
|
|
});
|
|
|
|
// Mettre à jour le statut des équipements
|
|
for (var equipment in event.assignedEquipment) {
|
|
final doc = await _equipmentCollection.doc(equipment.equipmentId).get();
|
|
if (doc.exists) {
|
|
await _updateEquipmentStatus(equipment.equipmentId, EquipmentStatus.inUse);
|
|
}
|
|
}
|
|
} catch (e) {
|
|
print('Error validating all preparation and loading: $e');
|
|
rethrow;
|
|
}
|
|
}
|
|
|
|
// === DÉCHARGEMENT + RETOUR ===
|
|
|
|
/// Valider déchargement ET retour en même temps
|
|
Future<void> validateAllUnloadingAndReturn(
|
|
String eventId,
|
|
Map<String, int>? returnedQuantities,
|
|
) async {
|
|
try {
|
|
final event = await _getEvent(eventId);
|
|
if (event == null) throw Exception('Event not found');
|
|
|
|
final updatedEquipment = event.assignedEquipment.map((eq) {
|
|
final returnedQty = returnedQuantities?[eq.equipmentId] ??
|
|
eq.returnedQuantity ??
|
|
eq.quantity;
|
|
return eq.copyWith(
|
|
isUnloaded: true,
|
|
isReturned: true,
|
|
returnedQuantity: returnedQty,
|
|
);
|
|
}).toList();
|
|
|
|
await _eventsCollection.doc(eventId).update({
|
|
'assignedEquipment': updatedEquipment.map((e) => e.toMap()).toList(),
|
|
'unloadingStatus': unloadingStatusToString(UnloadingStatus.completed),
|
|
'returnStatus': returnStatusToString(ReturnStatus.completed),
|
|
});
|
|
|
|
// Mettre à jour les statuts et stocks
|
|
for (var equipment in updatedEquipment) {
|
|
final equipmentDoc = await _equipmentCollection.doc(equipment.equipmentId).get();
|
|
if (equipmentDoc.exists) {
|
|
final equipmentData = EquipmentModel.fromMap(
|
|
equipmentDoc.data() as Map<String, dynamic>,
|
|
equipmentDoc.id,
|
|
);
|
|
|
|
if (!equipmentData.hasQuantity) {
|
|
await _updateEquipmentStatus(equipment.equipmentId, EquipmentStatus.available);
|
|
}
|
|
|
|
if (equipmentData.hasQuantity && equipment.returnedQuantity != null) {
|
|
final currentAvailable = equipmentData.availableQuantity ?? 0;
|
|
await _equipmentCollection.doc(equipment.equipmentId).update({
|
|
'availableQuantity': currentAvailable + equipment.returnedQuantity!,
|
|
'updatedAt': Timestamp.fromDate(DateTime.now()),
|
|
});
|
|
}
|
|
}
|
|
}
|
|
} catch (e) {
|
|
print('Error validating all unloading and return: $e');
|
|
rethrow;
|
|
}
|
|
}
|
|
|
|
// === HELPERS ===
|
|
|
|
Future<void> _updateEquipmentStatus(String equipmentId, EquipmentStatus status) async {
|
|
try {
|
|
final doc = await _equipmentCollection.doc(equipmentId).get();
|
|
if (!doc.exists) return;
|
|
|
|
await _equipmentCollection.doc(equipmentId).update({
|
|
'status': equipmentStatusToString(status),
|
|
'updatedAt': Timestamp.fromDate(DateTime.now()),
|
|
});
|
|
} catch (e) {
|
|
print('Error updating equipment status: $e');
|
|
}
|
|
}
|
|
|
|
Future<EventModel?> _getEvent(String eventId) async {
|
|
try {
|
|
final doc = await _eventsCollection.doc(eventId).get();
|
|
if (doc.exists) {
|
|
return EventModel.fromMap(doc.data() as Map<String, dynamic>, doc.id);
|
|
}
|
|
return null;
|
|
} catch (e) {
|
|
print('Error getting event: $e');
|
|
rethrow;
|
|
}
|
|
}
|
|
}
|
|
|