diff --git a/docs/adr/020-librairies-flutter.md b/docs/adr/020-librairies-flutter.md index 58407ce..da33737 100644 --- a/docs/adr/020-librairies-flutter.md +++ b/docs/adr/020-librairies-flutter.md @@ -14,9 +14,9 @@ L'application mobile RoadWave (iOS/Android) nécessite des librairies tierces po ## Décision -Utilisation de **8 librairies open-source** Flutter avec licences permissives. +Utilisation de **9 librairies open-source** Flutter avec licences permissives, déployées en 2 phases selon la stratégie définie dans [ADR-017 (Notifications Géolocalisées)](017-notifications-geolocalisees.md). -### Core Stack +### Phase 1 (MVP) : Core Stack | Catégorie | Librairie | Licence | Justification | |-----------|-----------|---------|---------------| @@ -26,21 +26,29 @@ Utilisation de **8 librairies open-source** Flutter avec licences permissives. | **Stockage sécurisé** | `flutter_secure_storage` | BSD-3 | Keychain iOS, KeyStore Android | | **Cache images** | `cached_network_image` | MIT | LRU cache, placeholder support | -### Géolocalisation & Permissions +### Phase 1 (MVP) : Géolocalisation & Notifications | Catégorie | Librairie | Licence | Justification | |-----------|-----------|---------|---------------| -| **GPS temps réel** | `geolocator` | MIT | Mode voiture, high accuracy, background modes | -| **Geofencing** | `geofence_service` | MIT | Détection rayon 200m, mode piéton, économie batterie | +| **GPS temps réel** | `geolocator` | MIT | Mode voiture, WebSocket position updates, high accuracy | +| **Push notifications** | `firebase_messaging` | BSD-3 | FCM tokens, notifications serveur (ADR-017) | | **Notifications locales** | `flutter_local_notifications` | BSD-3 | Compteur dynamique, icônes custom, iOS/Android | +| **Permissions** | `permission_handler` | MIT | Gestion unifiée permissions iOS/Android | -### Packages Additionnels (CarPlay/Android Auto) +### Phase 1 (MVP) : CarPlay/Android Auto (optionnel) | Catégorie | Librairie | Licence | Justification | |-----------|-----------|---------|---------------| | **CarPlay** | `flutter_carplay` | MIT | Intégration CarPlay native (communautaire) | | **Android Auto** | `android_auto_flutter` | Apache-2.0 | Support Android Auto (communautaire) | -| **Permissions** | `permission_handler` | MIT | Gestion unifiée permissions iOS/Android | + +### Phase 2 (Post-MVP) : Geofencing Local + +| Catégorie | Librairie | Licence | Justification | Voir ADR | +|-----------|-----------|---------|---------------|----------| +| **Geofencing local** | `geofence_service` | MIT | Mode offline, détection rayon 200m, notifications app fermée | [ADR-017](017-notifications-geolocalisees.md) Phase 2 | + +**Note importante** : Le geofencing local (`geofence_service`) n'est **PAS utilisé en MVP**. La Phase 1 utilise WebSocket + Firebase pour les notifications de proximité (voir [ADR-017](017-notifications-geolocalisees.md) pour l'architecture complète). ## Alternatives considérées @@ -60,11 +68,21 @@ Utilisation de **8 librairies open-source** Flutter avec licences permissives. - **location** : Moins maintenu - **background_location** : Spécifique background uniquement +### Notifications Push +- **firebase_messaging** (choisi) : Gratuit, 99.95% uptime, intégration native iOS/Android +- **OneSignal** : Plus cher (500€/mois @ 100K users) +- **Custom WebSocket** : Complex, toujours besoin APNS/FCM au final (voir ADR-017) + +### Geofencing (Phase 2) +- **geofence_service** (choisi) : Natif iOS/Android, économie batterie optimale +- **background_geolocation** : Payant (149$/an par app) +- **flutter_background_location** : Moins mature + ## Justification ### Licences -- **7/8 librairies** : MIT (permissive totale) -- **1/8** : BSD-3 (permissive, compatible commercial) +- **7/9 librairies** : MIT (permissive totale) +- **2/9** : BSD-3 (permissive, compatible commercial) - **Compatibilité totale** : Aucun conflit de licence, aucune restriction commerciale ### Maturité @@ -77,12 +95,14 @@ Utilisation de **8 librairies open-source** Flutter avec licences permissives. - **Compilation native** : Dart → ARM64 (pas de bridge JS comme React Native) - **just_audio** : Utilise AVPlayer (iOS) et ExoPlayer (Android) natifs - **geolocator** : Accès direct CoreLocation (iOS) et FusedLocation (Android) -- **geofence_service** : Geofencing natif, minimise consommation batterie +- **firebase_messaging** : Utilise services systèmes (Google Play Services, APNS) +- **geofence_service** (Phase 2) : Geofencing natif, minimise consommation batterie ### Conformité Stores - **Permissions progressives** : `permission_handler` + stratégie ADR-010 -- **Background modes** : `geolocator` + `geofence_service` approuvés stores -- **Notifications** : `flutter_local_notifications` conforme guidelines iOS/Android +- **Background modes MVP** : `geolocator` (When In Use) + `firebase_messaging` approuvés stores +- **Background modes Phase 2** : `geofence_service` nécessite permission "Always" (taux acceptation ~30%) +- **Notifications** : `flutter_local_notifications` + `firebase_messaging` conformes guidelines iOS/Android ## Architecture @@ -99,14 +119,18 @@ graph TB Cache["cached_network_image
(Image Cache)"] end - subgraph Services["Services Layer"] + subgraph Services["Services Layer - Phase 1 MVP"] Audio["just_audio
(HLS Streaming)"] - GPS["geolocator
(GPS Mode Voiture)"] - Geofence["geofence_service
(Mode Piéton)"] - Notif["flutter_local_notifications
(Alerts Locales)"] + GPS["geolocator
(GPS + WebSocket)"] + FCM["firebase_messaging
(Push Serveur)"] + Notif["flutter_local_notifications
(Notifications Locales)"] Perms["permission_handler
(Permissions iOS/Android)"] end + subgraph Phase2["Services Layer - Phase 2"] + Geofence["geofence_service
(Mode Offline)"] + end + subgraph Platform["Platform Integration"] CarPlay["flutter_carplay
(iOS)"] AndroidAuto["android_auto_flutter
(Android)"] @@ -116,14 +140,17 @@ graph TB Bloc --> API Bloc --> Audio Bloc --> GPS - Bloc --> Geofence + Bloc --> FCM API --> Storage Widgets --> Cache GPS --> Perms - Geofence --> Perms - Geofence --> Notif + FCM --> Perms + FCM --> Notif + + Geofence -.->|Phase 2| Perms + Geofence -.->|Phase 2| Notif Audio --> CarPlay Audio --> AndroidAuto @@ -135,7 +162,8 @@ graph TB class UI,Widgets,Bloc uiStyle class Data,API,Storage,Cache dataStyle - class Services,Audio,GPS,Geofence,Notif,Perms serviceStyle + class Services,Audio,GPS,FCM,Notif,Perms serviceStyle + class Phase2,Geofence serviceStyle class Platform,CarPlay,AndroidAuto platformStyle ``` @@ -151,7 +179,8 @@ graph TB ### Négatives - ⚠️ **CarPlay/Android Auto** : Packages communautaires (pas officiels Flutter) -- ⚠️ **Géolocalisation background** : Scrutée par App Store (stratégie progressive requise, ADR-010) +- ⚠️ **Firebase dépendance** : Vendor lock-in Google (mitigé par abstraction layer, voir ADR-017) +- ⚠️ **Permission "Always" Phase 2** : Taux acceptation ~30% (geofencing local) - ❌ **Courbe d'apprentissage** : Dart + pattern BLoC à maîtriser - ❌ **Tests stores** : Validation TestFlight (iOS) et Internal Testing (Android) obligatoires @@ -159,23 +188,26 @@ graph TB > **Note** : Les versions exactes seront définies lors de l'implémentation. Cette section indique les packages requis, non les versions à utiliser (qui évoluent rapidement dans l'écosystème Flutter). -**Core** : +**Core (Phase 1 MVP)** : - `flutter_bloc` - State management - `just_audio` - Audio HLS streaming - `dio` - HTTP client - `flutter_secure_storage` - Stockage sécurisé JWT - `cached_network_image` - Cache images -**Géolocalisation & Notifications** : -- `geolocator` - GPS haute précision -- `geofence_service` - Geofencing arrière-plan +**Géolocalisation & Notifications (Phase 1 MVP)** : +- `geolocator` - GPS haute précision, WebSocket position updates +- `firebase_messaging` - Push notifications serveur (ADR-017) - `flutter_local_notifications` - Notifications locales - `permission_handler` - Gestion permissions -**CarPlay/Android Auto** (optionnels MVP) : +**CarPlay/Android Auto (optionnels Phase 1)** : - `flutter_carplay` - Intégration CarPlay - `android_auto_flutter` - Support Android Auto +**Geofencing (Phase 2 Post-MVP)** : +- `geofence_service` - Geofencing local pour mode offline (ADR-017 Phase 2) + ### Migration depuis ADR-010 La section "Packages clés" de l'ADR-010 est désormais obsolète et doit référencer cet ADR : @@ -190,7 +222,8 @@ La section "Packages clés" de l'ADR-010 est désormais obsolète et doit réfé ### Risque 2 : Validation App Store (permissions background) - **Impact** : Taux de rejet ~70% si mal justifié -- **Mitigation** : Stratégie progressive (ADR-010), écrans d'éducation, tests beta TestFlight +- **Mitigation Phase 1** : Permission "When In Use" seulement (MVP), moins scrutée par Apple +- **Mitigation Phase 2** : Stratégie progressive (ADR-010), écrans d'éducation, tests beta TestFlight pour permission "Always" ### Risque 3 : Performance audio HLS en arrière-plan - **Impact** : Interruptions si OS tue l'app @@ -198,10 +231,13 @@ La section "Packages clés" de l'ADR-010 est désormais obsolète et doit réfé ## Références -- ADR-010 : Frontend Mobile (Flutter, architecture permissions) -- ADR-018 : Librairies Go (même format de documentation) +- [ADR-010 : Frontend Mobile](010-frontend-mobile.md) (Flutter, architecture permissions) +- [ADR-017 : Notifications Géolocalisées](017-notifications-geolocalisees.md) (Phase 1 WebSocket vs Phase 2 Geofencing) +- [ADR-018 : Librairies Go](018-librairies-go.md) (même format de documentation) - [flutter_bloc documentation](https://bloclibrary.dev/) - [just_audio repository](https://pub.dev/packages/just_audio) - [geolocator documentation](https://pub.dev/packages/geolocator) +- [firebase_messaging documentation](https://pub.dev/packages/firebase_messaging) +- [geofence_service documentation](https://pub.dev/packages/geofence_service) - [Apple CarPlay Developer Guide](https://developer.apple.com/carplay/) - [Android Auto Developer Guide](https://developer.android.com/training/cars)