createUser method
- RaliUser user
//////////// //////////// Creates a new user document in Firestore with transaction safety
Implementation
// II.C - CRUD Operations
///////////////
/// Creates a new user document in Firestore with transaction safety
Future<void> createUser(RaliUser user) async {
try {
// Use transaction to ensure data consistency
await _firestore.runTransaction((transaction) async {
final userDocRef = _firestore.collection(_collectionPath).doc(user.uid);
final userDoc = await transaction.get(userDocRef);
// Check if user already exists to prevent duplicates
if (userDoc.exists) {
// Only update lastLogin if user exists
transaction.update(userDocRef, {
'lastLogin': FieldValue.serverTimestamp(),
});
} else {
// Create new user with server timestamp
final userData = user.toMap();
// Ensure timestamps are handled properly
userData['createdAt'] = FieldValue.serverTimestamp();
userData['lastLogin'] = FieldValue.serverTimestamp();
transaction.set(userDocRef, userData);
}
});
// Update local cache
_userCache[user.uid] = user;
} catch (e) {
print('Error creating user: $e');
// Provide more detailed error information
if (e is FirebaseException) {
if (e.code == 'permission-denied') {
throw RALIException('Permission denied while creating user profile', cause: e);
} else if (e.code == 'unavailable') {
// Store in local cache for offline support
_userCache[user.uid] = user;
// Track that entire user needs to be created when back online
_pendingChanges[user.uid] = {'__create': true, ...user.toMap()};
throw RALIException('Network unavailable, user will be synced when online', cause: e);
}
}
throw RALIException('Failed to create user profile', cause: e);
}
}