Un client Android natif construit face à une API REST d'offres d'emploi : s'inscrire ou se connecter, parcourir des offres paginées, et conserver localement celles sur lesquelles revenir — avec le cycle de vie du jeton et la couche HTTP traités une seule fois, au même endroit, plutôt que redéfinis dans chaque écran.
Le problème et les contraintes
Un client mobile face à une API authentifiée pose trois problèmes faciles à mal résoudre : le jeton arrive après le démarrage et change à la connexion/déconnexion, chaque requête a besoin des mêmes en-têtes, et reconstruire la pile HTTP à chaque appel jette silencieusement le pool de connexions. La contrainte était de rassembler tout cela en un seul endroit, pour que les activités ne manipulent que des appels typés et des résultats.
Approche
- Une instance Retrofit unique, mise en cache statiquement et reconstruite uniquement quand le jeton change réellement, afin que les pools de connexions et de threads d'OkHttp survivent d'une requête à l'autre.
- Un intercepteur OkHttp ajoute
Accept: application/jsonet, si un jeton est présent,Authorization: Bearer …— les écrans ne touchent jamais aux en-têtes. - Surface d'API découpée par responsabilité en interfaces typées :
AuthApi(inscription / connexion / déconnexion / profil) etJobsApi(liste / création), avec un conteneur génériquePagedResponse<T>pour que la pagination soit modélisée une fois et non par endpoint. - Favoris basculés localement sous forme d'un
Set<String>d'identifiants d'offres : la liste survit aux redémarrages et reste lisible sans aller-retour réseau.
Description complète :
- activities — typed calls only → AuthApi — register, login, — logout, me
- activities — typed calls only → JobsApi — list, create — PagedResponse<T>
- activities — typed calls only → SharedPreferences — favorites: Set<String> (local)
- AuthApi — register, login, — logout, me → Retrofit + OkHttp — cached, keyed on token — Accept + Bearer
- JobsApi — list, create — PagedResponse<T> → Retrofit + OkHttp — cached, keyed on token — Accept + Bearer
- Retrofit + OkHttp — cached, keyed on token — Accept + Bearer → job-board API (bearer)
Compromis faits
Decision
Une instance Retrofit mise en cache et indexée sur le jeton, plutôt qu'une par appel : préserve la réutilisation des connexions et évite de réallouer le client à chaque requête, au prix d'une logique d'invalidation explicite — l'instance doit savoir quand le jeton a changé, un petit état que j'assume au lieu de l'éviter.
Decision
Les favoris dans SharedPreferences plutôt que dans une table Room : un ensemble d'identifiants entiers n'a besoin ni de schéma, ni de migration, ni de DAO, et le coût de lecture/écriture est négligeable à cette taille. Room et WorkManager sont en place pour le chemin de synchronisation, là où un vrai miroir local des offres a besoin de structure.
Résultats
Une boucle fonctionnelle connexion → parcours paginé → mise en favori face à une API réelle, avec les préoccupations HTTP et d'authentification isolées derrière deux interfaces et un intercepteur au lieu d'être disséminées dans les activités.
Ce que je referais différemment
Conditionner HttpLoggingInterceptor en Level.BODY à
BuildConfig.DEBUG — en l'état, un build de production écrirait les
jetons Bearer et les corps de réponse complets dans logcat, et c'est le
seul changement que je ferais avant de publier quoi que ce soit. Je
déplacerais aussi les favoris côté serveur : ils sont aujourd'hui liés à
l'appareil, donc le même compte sur un second téléphone repart vide.