292 lines
7.7 KiB
Dart
292 lines
7.7 KiB
Dart
import 'package:cloud_firestore/cloud_firestore.dart';
|
|
import 'package:firebase_auth/firebase_auth.dart';
|
|
import '../blocs/user/user_state.dart';
|
|
|
|
class UserService {
|
|
final FirebaseFirestore _firestore;
|
|
final FirebaseAuth _auth;
|
|
static const String _usersCollection = 'users';
|
|
|
|
UserService({
|
|
FirebaseFirestore? firestore,
|
|
FirebaseAuth? auth,
|
|
}) : _firestore = firestore ?? FirebaseFirestore.instance,
|
|
_auth = auth ?? FirebaseAuth.instance;
|
|
|
|
// Obtenir l'utilisateur connecté actuel
|
|
User? getCurrentFirebaseUser() {
|
|
return _auth.currentUser;
|
|
}
|
|
|
|
// Obtenir l'ID de l'utilisateur connecté
|
|
String? getCurrentUserId() {
|
|
return _auth.currentUser?.uid;
|
|
}
|
|
|
|
// Créer un nouvel utilisateur dans Firestore
|
|
Future<bool> createUser(UserModel user) async {
|
|
try {
|
|
await _firestore
|
|
.collection(_usersCollection)
|
|
.doc(user.id)
|
|
.set(user.toJson());
|
|
return true;
|
|
} catch (e) {
|
|
print('Erreur lors de la création de l\'utilisateur: $e');
|
|
return false;
|
|
}
|
|
}
|
|
|
|
// Obtenir un utilisateur par son ID
|
|
Future<UserModel?> getUserById(String userId) async {
|
|
try {
|
|
final doc = await _firestore
|
|
.collection(_usersCollection)
|
|
.doc(userId)
|
|
.get();
|
|
|
|
if (doc.exists) {
|
|
return UserModel.fromJson({
|
|
'id': doc.id,
|
|
...doc.data() as Map<String, dynamic>,
|
|
});
|
|
}
|
|
return null;
|
|
} catch (e) {
|
|
print('Erreur lors de la récupération de l\'utilisateur: $e');
|
|
return null;
|
|
}
|
|
}
|
|
|
|
// Obtenir un utilisateur par son email
|
|
Future<UserModel?> getUserByEmail(String email) async {
|
|
try {
|
|
final querySnapshot = await _firestore
|
|
.collection(_usersCollection)
|
|
.where('email', isEqualTo: email)
|
|
.limit(1)
|
|
.get();
|
|
|
|
if (querySnapshot.docs.isNotEmpty) {
|
|
final doc = querySnapshot.docs.first;
|
|
return UserModel.fromJson({
|
|
'id': doc.id,
|
|
...doc.data(),
|
|
});
|
|
}
|
|
return null;
|
|
} catch (e) {
|
|
print('Erreur lors de la récupération de l\'utilisateur par email: $e');
|
|
return null;
|
|
}
|
|
}
|
|
|
|
// Obtenir l'ID d'un utilisateur par son email
|
|
Future<String?> getUserIdByEmail(String email) async {
|
|
try {
|
|
final querySnapshot = await _firestore
|
|
.collection(_usersCollection)
|
|
.where('email', isEqualTo: email)
|
|
.limit(1)
|
|
.get();
|
|
|
|
if (querySnapshot.docs.isNotEmpty) {
|
|
return querySnapshot.docs.first.id;
|
|
}
|
|
return null;
|
|
} catch (e) {
|
|
print('Erreur lors de la récupération de l\'ID utilisateur: $e');
|
|
return null;
|
|
}
|
|
}
|
|
|
|
// Mettre à jour un utilisateur
|
|
Future<bool> updateUser(String userId, Map<String, dynamic> userData) async {
|
|
try {
|
|
await _firestore
|
|
.collection(_usersCollection)
|
|
.doc(userId)
|
|
.update(userData);
|
|
return true;
|
|
} catch (e) {
|
|
print('Erreur lors de la mise à jour de l\'utilisateur: $e');
|
|
return false;
|
|
}
|
|
}
|
|
|
|
// Supprimer un utilisateur
|
|
Future<bool> deleteUser(String userId) async {
|
|
try {
|
|
await _firestore
|
|
.collection(_usersCollection)
|
|
.doc(userId)
|
|
.delete();
|
|
return true;
|
|
} catch (e) {
|
|
print('Erreur lors de la suppression de l\'utilisateur: $e');
|
|
return false;
|
|
}
|
|
}
|
|
|
|
// Vérifier si un email existe déjà
|
|
Future<bool> emailExists(String email) async {
|
|
try {
|
|
final querySnapshot = await _firestore
|
|
.collection(_usersCollection)
|
|
.where('email', isEqualTo: email)
|
|
.limit(1)
|
|
.get();
|
|
|
|
return querySnapshot.docs.isNotEmpty;
|
|
} catch (e) {
|
|
print('Erreur lors de la vérification de l\'email: $e');
|
|
return false;
|
|
}
|
|
}
|
|
|
|
// Obtenir plusieurs utilisateurs par leurs IDs
|
|
Future<List<UserModel>> getUsersByIds(List<String> userIds) async {
|
|
try {
|
|
if (userIds.isEmpty) return [];
|
|
|
|
final List<UserModel> users = [];
|
|
|
|
// Firestore a une limite de 10 éléments pour les requêtes 'in'
|
|
// Donc on divise en chunks de 10
|
|
for (int i = 0; i < userIds.length; i += 10) {
|
|
final chunk = userIds.skip(i).take(10).toList();
|
|
|
|
final querySnapshot = await _firestore
|
|
.collection(_usersCollection)
|
|
.where(FieldPath.documentId, whereIn: chunk)
|
|
.get();
|
|
|
|
for (var doc in querySnapshot.docs) {
|
|
users.add(UserModel.fromJson({
|
|
'id': doc.id,
|
|
...doc.data(),
|
|
}));
|
|
}
|
|
}
|
|
|
|
return users;
|
|
} catch (e) {
|
|
print('Erreur lors de la récupération des utilisateurs: $e');
|
|
return [];
|
|
}
|
|
}
|
|
|
|
// Obtenir tous les utilisateurs (à utiliser avec précaution)
|
|
Future<List<UserModel>> getAllUsers() async {
|
|
try {
|
|
final querySnapshot = await _firestore
|
|
.collection(_usersCollection)
|
|
.get();
|
|
|
|
return querySnapshot.docs.map((doc) {
|
|
return UserModel.fromJson({
|
|
'id': doc.id,
|
|
...doc.data(),
|
|
});
|
|
}).toList();
|
|
} catch (e) {
|
|
print('Erreur lors de la récupération de tous les utilisateurs: $e');
|
|
return [];
|
|
}
|
|
}
|
|
|
|
// Stream pour écouter les changements d'un utilisateur
|
|
Stream<UserModel?> getUserStream(String userId) {
|
|
return _firestore
|
|
.collection(_usersCollection)
|
|
.doc(userId)
|
|
.snapshots()
|
|
.map((doc) {
|
|
if (doc.exists) {
|
|
return UserModel.fromJson({
|
|
'id': doc.id,
|
|
...doc.data() as Map<String, dynamic>,
|
|
});
|
|
}
|
|
return null;
|
|
});
|
|
}
|
|
|
|
// Rechercher des utilisateurs par nom ou email
|
|
Future<List<UserModel>> searchUsers(String query) async {
|
|
try {
|
|
if (query.isEmpty) return [];
|
|
|
|
final queryLower = query.toLowerCase();
|
|
|
|
// Recherche par email
|
|
final emailResults = await _firestore
|
|
.collection(_usersCollection)
|
|
.where('email', isGreaterThanOrEqualTo: queryLower)
|
|
.where('email', isLessThanOrEqualTo: '$queryLower\uf8ff')
|
|
.limit(10)
|
|
.get();
|
|
|
|
// Recherche par prénom
|
|
final prenomResults = await _firestore
|
|
.collection(_usersCollection)
|
|
.where('prenom', isGreaterThanOrEqualTo: queryLower)
|
|
.where('prenom', isLessThanOrEqualTo: '$queryLower\uf8ff')
|
|
.limit(10)
|
|
.get();
|
|
|
|
// Combiner et dédupliquer les résultats
|
|
final Map<String, UserModel> usersMap = {};
|
|
|
|
for (var doc in emailResults.docs) {
|
|
usersMap[doc.id] = UserModel.fromJson({
|
|
'id': doc.id,
|
|
...doc.data(),
|
|
});
|
|
}
|
|
|
|
for (var doc in prenomResults.docs) {
|
|
usersMap[doc.id] = UserModel.fromJson({
|
|
'id': doc.id,
|
|
...doc.data(),
|
|
});
|
|
}
|
|
|
|
return usersMap.values.toList();
|
|
} catch (e) {
|
|
print('Erreur lors de la recherche d\'utilisateurs: $e');
|
|
return [];
|
|
}
|
|
}
|
|
|
|
// Mettre à jour la dernière connexion de l'utilisateur
|
|
Future<bool> updateLastLogin(String userId) async {
|
|
try {
|
|
await _firestore
|
|
.collection(_usersCollection)
|
|
.doc(userId)
|
|
.update({
|
|
'lastLogin': FieldValue.serverTimestamp(),
|
|
});
|
|
return true;
|
|
} catch (e) {
|
|
print('Erreur lors de la mise à jour de la dernière connexion: $e');
|
|
return false;
|
|
}
|
|
}
|
|
|
|
// Vérifier si l'utilisateur existe dans Firestore
|
|
Future<bool> userExists(String userId) async {
|
|
try {
|
|
final doc = await _firestore
|
|
.collection(_usersCollection)
|
|
.doc(userId)
|
|
.get();
|
|
return doc.exists;
|
|
} catch (e) {
|
|
print('Erreur lors de la vérification de l\'existence de l\'utilisateur: $e');
|
|
return false;
|
|
}
|
|
}
|
|
}
|