đ§ Android Architecture Component Introduction
Note đ: Cette fiche vous permet de comprendre et d'avoir une rapide rĂ©fĂ©rence sur ce que sont les architectures components. Avec un exercice pratique.
Imaginez le scénario suivant
- L'application se lance, votre app doit récupérer depuis le réseau le nom de l'utilisateur
- Au lancement, le réseau est lent, et votre interface ne peut se permettre d'afficher juste un écran blanc.
- Vous allez devoir surveiller quand la requĂȘte rĂ©seau est terminĂ©e
- Lorsque la requĂȘte est terminĂ©, vous devez afficher le nom de l'utilisateur, puis faire disparaitre le
loader
qui faisait patienter votre utilisateur. - Sauf que, si l'utilisateur fait une rotation du tĂ©lĂ©phone, votre activity est dĂ©truite puis recréée (CF schema lifecyle). Vous devez donc gĂ©rer la fuite mĂ©moire qui en dĂ©coule et stopper la requĂȘte rĂ©seau si l'
activity
passe dansonDestroy()
, puis relancer la requĂȘte dansonCreate()
uniquement si cela s'est mal passĂ©. - Les donnĂ©es doivent aussi ĂȘtre sauvegardĂ©e dans un Bundle pour ĂȘtre rĂ©affichĂ©es depuis le cache lors d'une rotation ou d'un
onPause()
- Bonus : Imaginez avoir des fragments par dessus l'activitĂ©, ayant des lifecyle Ă gĂ©rer -> â ïž
Ca donnerait ça (en pseudo code)
var user : User? = null
private lateinit var loader : Loader
const val USERNAME_BUNDLE_KEY = "username"
var firstLaunch = true
fun onDestroy() {
NetworkService.cancelAllOperations()
}
fun onResume(){
if(savedInstanceState != null){
usernameSaved = savedInstanceState.string(USERNAME_BUNDLE_KEY);
} else {
//SSI on a pas déjà les données
myNetworkRequest().launch(callback = gatheringResultFromNetwork)
}
//Et il faut gérer l'UI etc.
}
//onCreate()
fun onCreate(){
if(savedInstanceState != null && !firstLaunch){
usernameSaved = savedInstanceState.string(USERNAME_BUNDLE_KEY);
val textViewUser = findViewById<TextView>(R.id.usernameTextView)
textViewUser.text = usernameSaved
}
if(firstLaunch){
myNetworkRequest().launch(callback = gatheringResultFromNetwork)
}
var loader = findViewById<Loader>(R.id.loader)
loader.isVisible = true
}
fun gatheringResultFromNetwork() {
if(result){
user = result.parseJson.user
var textView = findViewById<TextView>(R.id.usernameTextView)
firstLaunch = false
Globalscope.launch(Dispatchers.Main){
textView.text = user.name
loader.isVisible = false
}
}
}
fun onSaveInstanceState(Bundle outState) {
outState.putInt(userName, user.name);
super.onSaveInstanceState(outState);
}
La mĂȘme chose en utilisant quelques outils des architectures components
//MainActivity.kt
var viewModel: UserViewModel by viewModels()
fun onCreate(){
//On link notre view model avec la vue XML
binding.viewModel = viewModel
//On dit que tout action est liée au lifycle de notre activity
binding.lifecycleOwner = this
}
<!-- main_activity.xml -->
<data>
<variable
name="viewModel"
type="com.example.android.UserViewModel" />
</data>
<Layout>
<TextView
android:id="@+id/usernameTextView"
...
android:text="@{String.valueOf(viewModel.user.name)}"
... />
</Layout>
C'est quand mĂȘme plus sympa non ?

Mais alors qu'est ce qui se passe exactement ?
Simplement on utilise une architecture MVVM qui est de surcroit réactive, avec des composants qui s'imbriquent trÚs bien entre eux :
- Le DataBinding (UI Components)
- Les LiveData et ViewModel
- Le Lifecycle

Une explication simple de la réactivité de cette architecture
Ces composants, utilisés ensemble, vont vous permettre d'avoir peu de code à maintenir, tout en ayant une app bien plus stable.
Pour faire simple, il faut savoir utiliser cela si vous voulez ĂȘtre efficace et rentable dans votre travail de dĂ©veloppeur Android.
Mais mĂȘme plus, il faut que vous soyez Ă l'affĂ»t des nouveautĂ©s pour constamment optimiser votre workflow et vos pratiques.
Les éléments d'architectures que vous devez comprendre
MVVM
C'est une architecture, tout comme l'est MVC. Une maniĂšre d'organiser votre code, mais aussi de faire communiquer vos composants entre eux.
Il en existe d'autres, mais Google Ă choisi de pousser cette architecture avec Jetpack.

Lifecycle
C'est une bibliothĂšque qui intĂšgre un certain nombre d'API permettant soit de s'abonner Ă un cycle de vie, soit de s'approprier un cycle de vie.
Live Data
Un des composants principaux que vous allez utiliser est le LiveData
, ce composant permet de rendre réactif et lifecycle aware n'importe quelle donnée dans votre application.
ViewModel
En suivant l'architecture MVVM, le viewModel est une piÚce importante de notre code. Il permet d'exposer les sources de données de maniÚre réactive, ainsi une vue peut s'abonner à une ou plusieurs sources de données afin de mettre à jour l'interface.
Le viewModel ne connait pas la vue, mais la vue s'abonne aux données du viewModel.
La classe ViewModel est conçue pour stocker et gérer les données liées à l'interface utilisateur en tenant compte du cycle de vie. La classe ViewModel permet aux données de survivre aux changements de configuration tels que les rotations d'écran.
DataBinding (Optionnel)
Le binding est une chose, le databinding va plus loin en rendant votre code XML trĂšs puissant. Comme en VueJS
ou en React
vous pourrez directement depuis vos balise XML
(Equivalent du HTML
en web) appeler des fonctions, des variables et effectuer des opérations complexes.
C'est exactement le mĂȘme principe qui est en place sur Android depuis l'arrivĂ©e de Jetpack et Kotlin.
Donc le databinding, c'est le fait de faire s'abonner la vue XML directement à des valeurs retournée par l'activité ou le fragment.
Ainsi votre logique d'affichage, voire mĂȘme de la logique un peu plus complexe peut s'effectuer directement depuis le XML.
Pour en faire l'expérience suivez le codelab suivant Data Binding Basics, sinon passez à la suite.
Exercice sur les architectures components
Un peu de code !
- Effectuez la leçon 5 des codelabs qui permet de faire l'expĂ©rience de tout ce charabiat thĂ©orique âïž et rĂ©pondez aux questions suivantes.