- Ajout système complet de gestion des secteurs avec contours géographiques - Import des contours départementaux depuis GeoJSON - API REST pour la gestion des secteurs (/api/sectors) - Service de géolocalisation pour déterminer les secteurs - Migration base de données avec tables x_departements_contours et sectors_adresses - Interface Flutter pour visualisation et gestion des secteurs - Ajout thème sombre dans l'application - Corrections diverses et optimisations 🤖 Generated with [Claude Code](https://claude.ai/code) Co-Authored-By: Claude <noreply@anthropic.com>
12 KiB
Executable File
Guide de Gestion des Boîtes Hive dans GeoSector
Ce document explique comment les boîtes Hive sont gérées dans l'application GeoSector, particulièrement pendant les processus de connexion et déconnexion.
Table des matières
- Introduction
- Boîtes Hive utilisées
- Initialisation des boîtes Hive
- Services et repositories impliqués
- Processus de connexion (login)
- Processus de déconnexion (logout)
- Problèmes connus et solutions
- Bonnes pratiques
Introduction
Hive est une base de données NoSQL légère et rapide utilisée dans GeoSector pour stocker les données localement. Les données sont organisées en "boîtes" (boxes) qui peuvent être typées pour stocker des modèles spécifiques.
Dans cette application, Hive est utilisé pour :
- Stocker les données utilisateur et maintenir les sessions
- Conserver les données des opérations, secteurs et passages
- Permettre l'utilisation de l'application en mode hors ligne
Boîtes Hive utilisées
Les boîtes Hive sont définies dans lib/core/constants/app_keys.dart :
// Noms des boîtes Hive
static const String usersBoxName = 'users';
static const String operationsBoxName = 'operations';
static const String sectorsBoxName = 'sectors';
static const String passagesBoxName = 'passages';
static const String settingsBoxName = 'settings';
Chaque boîte stocke un type spécifique de données :
- users : Stocke les informations des utilisateurs (
UserModel) - operations : Stocke les opérations (
OperationModel) - sectors : Stocke les secteurs (
SectorModel) - passages : Stocke les passages (
PassageModel) - settings : Stocke les préférences utilisateur (non typée)
Initialisation des boîtes Hive
Actuellement, les boîtes Hive sont initialisées dès le démarrage de l'application dans main.dart :
// Initialiser Hive
await Hive.initFlutter();
// Enregistrer les adaptateurs Hive
Hive.registerAdapter(UserModelAdapter());
Hive.registerAdapter(OperationModelAdapter());
Hive.registerAdapter(SectorModelAdapter());
Hive.registerAdapter(PassageModelAdapter());
// Ouvrir les boîtes Hive
await Hive.openBox<UserModel>(AppKeys.userBoxName);
await Hive.openBox<OperationModel>(AppKeys.operationsBoxName);
await Hive.openBox<SectorModel>(AppKeys.sectorsBoxName);
await Hive.openBox<PassageModel>(AppKeys.passagesBoxName);
await Hive.openBox(AppKeys.settingsBoxName);
Problème d'initialisation précoce
Cette approche ouvre toutes les boîtes Hive dès le démarrage de l'application, même sur les pages publiques comme LandingPage où elles ne sont pas nécessaires. Cela explique pourquoi vous voyez les messages suivants dans la console :
Got object store box in database users.
Got object store box in database operations.
Got object store box in database sectors.
Got object store box in database passages.
Got object store box in database settings.
Solution recommandée
Pour optimiser l'initialisation des boîtes Hive, il est recommandé de :
- N'initialiser que la boîte
usersau démarrage (pour vérifier si un utilisateur est déjà connecté) - Initialiser les autres boîtes uniquement après une connexion réussie
Modification suggérée pour main.dart :
// Initialiser Hive
await Hive.initFlutter();
// Enregistrer les adaptateurs Hive
Hive.registerAdapter(UserModelAdapter());
Hive.registerAdapter(OperationModelAdapter());
Hive.registerAdapter(SectorModelAdapter());
Hive.registerAdapter(PassageModelAdapter());
// N'ouvrir que la boîte des utilisateurs au démarrage
await Hive.openBox<UserModel>(AppKeys.userBoxName);
await Hive.openBox(AppKeys.settingsBoxName); // Préférences générales
// Les autres boîtes seront ouvertes après connexion dans UserRepository.login()
Services et repositories impliqués
UserRepository
Le UserRepository est le principal gestionnaire des boîtes Hive et de l'authentification. Il est responsable de :
- L'initialisation des boîtes au démarrage de l'application
- La gestion des boîtes pendant les processus de connexion et déconnexion
- Le nettoyage et la recréation des boîtes lorsque nécessaire
- La gestion complète de l'authentification (connexion et déconnexion)
- L'affichage des overlays de chargement pendant les opérations d'authentification
- La redirection vers les pages appropriées après connexion/déconnexion
Note importante : Auparavant, l'application utilisait un service séparé
AuthServicepour gérer l'authentification. Cette classe a été supprimée et ses fonctionnalités ont été intégrées directement dansUserRepositorypour simplifier l'architecture et éviter les problèmes de synchronisation entre les deux classes.
Autres repositories spécialisés
- OperationRepository : Gère la boîte
operations - SectorRepository : Gère la boîte
sectors - PassageRepository : Gère la boîte
passages
Ces repositories sont injectés dans le UserRepository pour traiter les données spécifiques à chaque modèle.
Processus de connexion (login)
Le processus de connexion dans UserRepository.login() suit ces étapes :
-
Nettoyage initial :
- Suppression des boîtes non référencées (
auth,locations,messages) - Nettoyage adapté à la plateforme (Web, iOS, Android)
- Suppression des boîtes non référencées (
-
Préparation des boîtes :
- Appel à
_clearAndRecreateBoxes()pour vider et recréer les boîtes sans les fermer - Utilisation de
_ensureBoxIsOpen()pour garantir que les boîtes sont ouvertes
- Appel à
-
Appel API et traitement des données :
- Connexion via l'API
- Vérification que toutes les boîtes sont ouvertes avant le traitement
- Traitement des données reçues (opérations, secteurs, passages)
-
Gestion des erreurs :
- Tentatives de récupération en cas d'erreur
- Réouverture des boîtes si nécessaire
Code clé pour la connexion
// S'assurer que les boîtes sont ouvertes
await _ensureBoxIsOpen(AppKeys.operationsBoxName);
await _ensureBoxIsOpen(AppKeys.sectorsBoxName);
await _ensureBoxIsOpen(AppKeys.passagesBoxName);
// Traiter les données
await _processOperations(operationsData);
await _processSectors(sectorsData);
await _processPassages(passagesData);
Processus de déconnexion (logout)
Le processus de déconnexion dans UserRepository.logout() suit ces étapes :
-
Préparation :
- Récupération de l'utilisateur actuel avant nettoyage
- Déconnexion de la session API
- Réinitialisation du cache de l'utilisateur actuel
-
Nettoyage des données :
- Appel à
_deepCleanHiveBoxes()pour un nettoyage complet des boîtes Hive
- Appel à
Méthode _deepCleanHiveBoxes
La méthode _deepCleanHiveBoxes() est cruciale pour le processus de déconnexion et suit ces étapes :
-
Vidage des boîtes :
- Vidage de toutes les boîtes Hive ouvertes sans les fermer
- Gestion des erreurs pour chaque boîte avec typage spécifique
-
Nettoyage spécifique à la plateforme :
- Nettoyage adapté selon la plateforme (Web, iOS, Android)
- Utilisation de méthodes spécifiques comme
_clearIndexedDB()pour le web
-
Réinitialisation :
- Réinitialisation de l'API Service
Code clé pour la déconnexion
// Méthode logout
Future<bool> logout() async {
try {
// Récupérer l'utilisateur actuel avant de nettoyer les données
final currentUser = getCurrentUser();
// Déconnecter la session API
if (currentUser?.sessionId != null) {
await logoutAPI();
}
// Supprimer la session API
setSessionId(null);
// Réinitialiser le cache de l'utilisateur actuel
_cachedCurrentUser = null;
// Nettoyage complet des boîtes Hive
await _deepCleanHiveBoxes();
return true;
} catch (e) {
return false;
}
}
// Méthode de nettoyage des boîtes Hive
Future<void> _deepCleanHiveBoxes() async {
try {
// 1. Vider toutes les boîtes sans les fermer
if (Hive.isBoxOpen(AppKeys.userBoxName)) {
await Hive.box<UserModel>(AppKeys.userBoxName).clear();
}
if (Hive.isBoxOpen(AppKeys.operationsBoxName)) {
await Hive.box<OperationModel>(AppKeys.operationsBoxName).clear();
}
if (Hive.isBoxOpen(AppKeys.sectorsBoxName)) {
await Hive.box<SectorModel>(AppKeys.sectorsBoxName).clear();
}
// Vider les autres boîtes...
// 2. Nettoyage spécifique à la plateforme
if (kIsWeb) {
await _clearIndexedDB();
} else if (Platform.isIOS) {
await _cleanHiveFilesOnIOS();
} else if (Platform.isAndroid) {
await _cleanHiveFilesOnAndroid();
}
// 3. Réinitialiser l'API Service
_apiService.setSessionId(null);
} catch (e) {
debugPrint('Erreur lors du nettoyage des boîtes Hive: $e');
}
}
Problèmes connus et solutions
1. Initialisation précoce des boîtes Hive
Problème : Toutes les boîtes Hive sont ouvertes dès le démarrage de l'application, même sur les pages publiques où elles ne sont pas nécessaires.
Solution : Modifier main.dart pour n'ouvrir que les boîtes essentielles au démarrage (users et settings) et initialiser les autres boîtes uniquement après connexion.
2. Erreur "Box has already been closed"
Problème : Des erreurs se produisent lorsqu'on tente d'accéder à une boîte qui a été fermée prématurément.
Solution :
- Utiliser la méthode
_ensureBoxIsOpen()avant d'accéder à une boîte - Éviter de fermer les boîtes qui pourraient être utilisées plus tard
- Préférer
box.clear()àbox.close()pour vider les données sans fermer la boîte
3. Persistance indésirable des données entre sessions
Problème : Les données peuvent persister entre les sessions utilisateur, créant des conflits ou des fuites de données.
Solution : Utiliser _clearAndRecreateBoxes() lors de la déconnexion pour vider correctement toutes les boîtes sauf users.
Bonnes pratiques
Initialisation à la demande
-
Initialiser les boîtes uniquement lorsqu'elles sont nécessaires :
- N'ouvrir que les boîtes
usersetsettingsau démarrage - Initialiser les autres boîtes après connexion réussie
- Utiliser
_ensureBoxIsOpen()avant chaque accès à une boîte
- N'ouvrir que les boîtes
-
Centraliser la gestion des boîtes :
- Créer un service dédié à la gestion des boîtes Hive
- Utiliser des méthodes comme
openRequiredBoxes()etclearAllBoxes()
-
Optimiser pour les différentes plateformes :
- Adapter le nettoyage selon la plateforme (Web, iOS, Android)
- Utiliser des méthodes spécifiques comme
_clearIndexedDB()pour le web
Éviter l'erreur "Box has already been closed"
-
Ne jamais fermer une boîte qui pourrait être utilisée plus tard :
- Utiliser
_ensureBoxIsOpen()au lieu de fermer et rouvrir les boîtes - Vider les boîtes avec
box.clear()au lieu de les fermer
- Utiliser
-
Vérifier qu'une boîte est ouverte avant de l'utiliser :
if (!Hive.isBoxOpen(boxName)) { await Hive.openBox<T>(boxName); } -
Gestion des erreurs robuste :
- Toujours entourer les opérations Hive de blocs try/catch
- Prévoir des mécanismes de récupération en cas d'erreur
Méthode utilitaire _ensureBoxIsOpen
Cette méthode est cruciale pour garantir qu'une boîte est ouverte avant de l'utiliser :
Future<void> _ensureBoxIsOpen(String boxName) async {
try {
if (!Hive.isBoxOpen(boxName)) {
debugPrint('Ouverture de la boîte $boxName...');
if (boxName == AppKeys.passagesBoxName) {
await Hive.openBox<PassageModel>(boxName);
} else if (boxName == AppKeys.operationsBoxName) {
await Hive.openBox<OperationModel>(boxName);
} else if (boxName == AppKeys.sectorsBoxName) {
await Hive.openBox<SectorModel>(boxName);
} else if (boxName == AppKeys.userBoxName) {
await Hive.openBox<UserModel>(boxName);
} else {
await Hive.openBox(boxName);
}
debugPrint('Boîte $boxName ouverte avec succès');
}
} catch (e) {
debugPrint('Erreur lors de l\'ouverture de la boîte $boxName: $e');
throw Exception('Impossible d\'ouvrir la boîte $boxName: $e');
}
}
Ce guide devrait aider à comprendre et maintenir la gestion des boîtes Hive dans l'application GeoSector. Pour toute question ou problème, consultez la documentation de Hive ou contactez l'équipe de développement.