ViewModels va LiveData: Namunalar + AntiPatterns

Ko'rishlar va ViewModels

Vazifalarni taqsimlash

Arxitektura komponentlari bilan yaratilgan ilovada ob'ektlarning odatiy o'zaro ta'siri

Ideal holda, ViewModels Android haqida hech narsa bilmasligi kerak. Bu sinov qobiliyatini, oqish xavfsizligi va modullikni yaxshilaydi. Umumiy qoidalar android yo'qligiga ishonch hosil qilishdir. * ViewModels-ga import (android.arch. * Kabi istisnolardan tashqari). Xuddi shu narsa taqdimotchilarga ham tegishli.

View ViewModels (va Taqdimotchilar) ga Android tizim sinflari to'g'risida ma'lumot berishlariga yo'l qo'ymang

Shartlar, ko'chadan va umumiy qarorlar Faoliyat yoki Fragmentlarda emas, balki ViewModels-da yoki ilovaning boshqa qatlamlarida bajarilishi kerak. View odatda birlik tomonidan sinovdan o'tkazilmaydi (agar siz Robolectric-dan foydalanmasangiz), shunda kam satr kodlari yaxshiroq bo'ladi. Ko'rishlar faqat ma'lumotlarni qanday ko'rsatish va foydalanuvchi voqealarini ViewModelga (yoki Taqdimotchiga) qanday yuborishni bilishi kerak. Bunga Passiv ko'rinish namunasi deyiladi.

Faoliyatlar va qismlardan mantiqni minimal darajada saqlang

ViewModels-da havolalarni ko'rish

ViewModels-ning faoliyati yoki bo'laklariga qaraganda farqli jihatlari bor. ViewModel tirik va ishlayotgan vaqtda, faoliyat uning hayotiy tsiklining har qanday holatida bo'lishi mumkin. Faoliyat va parchalar ViewModel bilmagan holda yo'q qilinishi va qayta yaratilishi mumkin.

ViewModels konfiguratsiyadagi o'zgarishlar davom etmoqda

View ma'lumotnomasini (faoliyat yoki parcha) ViewModel-ga topshirish jiddiy xavf tug'diradi. Tasavvur qilaylik, ViewModel tarmoqdan ma'lumotlarni talab qiladi va ma'lumotlar birozdan keyin qaytib keladi. O'sha paytda, View ma'lumotnomasi yo'q qilinishi yoki eski ko'rinishi mumkin, bu xotira sızıntısını va, ehtimol, buzilishni keltirib chiqarishi mumkin.

View ViewModels-da "Ko'rishlar" ga murojaat qilishdan saqlaning.

ViewModels va Views o'rtasida aloqa qilishning tavsiya etilgan usuli bu LiveData yoki boshqa kutubxonalarning kuzatuvlaridan foydalangan holda kuzatuvchi naqshidir.

Kuzatuvchi namunasi

Android-da taqdimot qatlamini loyihalashning juda qulay usuli bu ViewModel-ni ko'rish (faoliyat yoki qism) ni kuzatish (o'zgartirishlarga obuna bo'lish). ViewModel Android haqida bilmaganligi sababli, Android-ning View-larni tez-tez qanday o'ldirishni yaxshi ko'rishini bilmaydi. Bu bir qator afzalliklarga ega:

  1. ViewModels konfiguratsiyani o'zgartirishda davom etadi, shuning uchun aylanish sodir bo'lganda ma'lumotlar uchun tashqi manbani (masalan, ma'lumotlar bazasi yoki tarmoq) qayta so'rashning hojati yo'q.
  2. Uzoq davom etadigan operatsiyalar tugaganda ViewModel-dagi kuzatiladigan narsalar yangilanadi. Ma'lumotlar kuzatiladimi yoki yo'qmi muhim emas. Mavjud bo'lmagan ko'rinishni yangilash paytida null ko'rsatkichlari uchun istisnolar mavjud emas.
  3. ViewModels ko'rinishga murojaat qilmaydi, shuning uchun xotira buzilishi xavfi kam bo'ladi.
UI-ga ma'lumotlarni kiritish o'rniga, foydalanuvchi interfeysi unga kiritilgan o'zgarishlarni kuzatishiga ruxsat bering.

Yog 'ko'rinishiModellar

Sizni tashvishlardan ajratishga imkon beradigan narsa yaxshi fikr. Agar sizning ViewModel kodingiz juda ko'p bo'lsa yoki juda ko'p majburiyatlarga ega bo'lsa:

  • ViewModel hajmi bilan bir xil bo'lgan mantiqiy so'zlarni taqdimotchiga o'tkazish. U sizning ilovangizning boshqa qismlari bilan aloqa o'rnatadi va ViewModel-dagi LiveData egalarini yangilaydi.
  • Domen qatlamini qo'shish va toza arxitekturani qabul qilish. Bu juda sinab ko'riladigan va saqlanadigan me'morchilikka olib keladi. Bundan tashqari, asosiy ipni tezda olishni osonlashtiradi. Architecture Blueprints-da toza arxitektura namunasi mavjud.
Mas'uliyatni taqsimlang, kerak bo'lsa domen qatlamini qo'shing.

Ma'lumotlar omboridan foydalanish

Ilovalar arxitekturasi qo'llanmasida ko'rinib turibdiki, ko'pgina ilovalarda bir nechta ma'lumotlar manbalari mavjud, masalan:

  1. Masofadan boshqarish: tarmoq yoki bulut
  2. Mahalliy: ma'lumotlar bazasi yoki fayl
  3. Xotirada kesh

O'zingizning taqdimot qatlamingizdan mutlaqo bexabar holda, ilovangizda ma'lumotlar qatlamiga ega bo'lish yaxshi fikr. Kesh va ma'lumotlar bazasini tarmoq bilan sinxronlashtirish uchun algoritmlar ahamiyatsiz emas. Ushbu murakkablik bilan shug'ullanadigan kirishning yagona nuqtasi sifatida alohida saqlash omboriga ega bo'lish tavsiya etiladi.

Agar sizda bir nechta va juda ko'p turli xil ma'lumotlar modellari bo'lsa, bir nechta omborxonalarni qo'shishni o'ylab ko'ring.

Ma'lumotlar omboriga ma'lumotlarni bitta nuqtali yozuv sifatida qo'shing

Ma'lumotlar holati bilan ishlash

Ushbu stsenariyni ko'rib chiqing: siz ViewModel tomonidan namoyish qilingan LiveData-ni ko'rmoqdasiz, unda namoyish etiladigan narsalar ro'yxati mavjud. Qanday qilib View yuklanayotgan ma'lumotlar, tarmoq xatosi va bo'sh ro'yxat o'rtasida farq qilishi mumkin?

  • Siz ViewModel-dan LiveData -ni ochishingiz mumkin. Masalan, MyDataState ma'lumotlar hozirgi vaqtda yuklanayotganligi, yuklanganligi yoki muvaffaqiyatsiz bo'lganligi to'g'risida ma'lumotni o'z ichiga olishi mumkin.

Siz xato xabari kabi davlat va boshqa metadata mavjud sinfga ma'lumotlarni o'rashingiz mumkin. Bizning namunalarimizdagi Resurslar sinfiga qarang.

O'ralgan yoki boshqa LiveData-dan foydalangan holda ma'lumotlarning holati to'g'risida ma'lumot bering.

Saqlash faoliyati holati

Faoliyat holati - bu yo'qolgan yoki jarayon o'ldirilgan degan ma'noni anglatadigan ekranni qayta tiklash uchun kerak bo'lgan ma'lumot. Aylantirish - bu eng aniq hodisa va biz ViewModels bilan qoplanganmiz. Agar u ViewModel-da saqlansa, davlat xavfsizdir.

Shunga qaramay, ViewModels-ning yo'qolgan boshqa stsenariylarida holatni tiklashingiz kerak bo'lishi mumkin: agar OT resurslari past bo'lsa va masalan, jarayoningizni o'ldirsa.

UI holatini samarali saqlash va tiklash uchun, onSaveInstanceState () va ViewModels-larda qat'iylik kombinatsiyasidan foydalaning.

Misol uchun, qarang: ViewModels: qat'iyatlilik, onSaveInstanceState (), UI va yuklovchilar holatini tiklash

Hodisalar

Hodisa - bu bir marta sodir bo'ladigan narsa. ViewModels ma'lumotlarni oshkor qiladi, ammo voqealar haqida nima deyish mumkin? Masalan, navigatsiya tadbirlari yoki Snackbar xabarlarini ko'rsatish bu faqat bir marta bajarilishi kerak bo'lgan harakatlardir.

Voqealar kontseptsiyasi LiveData ma'lumotlarni saqlash va qayta tiklash bilan to'liq mos kelmaydi. ViewModel-ni quyidagi maydon bilan ko'rib chiqing:

LiveData  snackbarMessage = yangi MutableLiveData <> ();

Harakat buni kuzatishni boshlaydi va ViewModel operatsiyani yakunlaydi, shuning uchun xabarni yangilash kerak:

snackbarMessage.setValue ("Element saqlandi!");

Faoliyat qiymatni oladi va Snackbar-ni ko'rsatadi. Aftidan, ishlaydi.

Ammo, agar foydalanuvchi telefonni aylantirsa, yangi harakat yaratiladi va kuzatishni boshlaydi. LiveData kuzatuvi boshlanganda, harakat darhol eski qiymatni oladi, bu xabarni yana ko'rsatishga olib keladi!

Buni arxitektura tarkibiy qismlariga kutubxonalar yoki kengaytmalar bilan hal qilishga urinishning o'rniga, uni dizayndagi muammolarga duch kelish kerak. O'zingizning voqealaringizni davlatning bir qismi sifatida ko'rib chiqishingizni tavsiya qilamiz.

O'zingizning davlatingiz sifatida tadbirlarni loyihalash. Qo'shimcha ma'lumot olish uchun LiveData-ni SnackBar, Navigatsiya va boshqa tadbirlarni o'qing (SingleLiveEvent ishi).

ViewModelsning oqishi

Reaktiv paradigma Android-da yaxshi ishlaydi, chunki u UI va ilovangizning qolgan qatlamlari o'rtasida qulay ulanishni ta'minlaydi. LiveData bu strukturaning asosiy qismidir, shuning uchun sizning faoliyatingiz va parchalaringiz LiveData nusxalarini kuzatadi.

ViewModels-ning boshqa tarkibiy qismlar bilan qanday aloqasi sizga bog'liq, ammo qochqinlar va chekka holatlarga e'tibor bering. Ushbu sxemani ko'rib chiqing: Taqdimot sathi kuzatuvchi andozasidan foydalangan holda va Layer Layer qayta qo'ng'iroqlarni ishlatishda:

UI va kuzatuv ma'lumotlari qatlamidagi qayta ulanishlarni kuzatuvchi naqsh

Agar foydalanuvchi ilovadan chiqsa, View yo'q qilinadi, shuning uchun ViewModel endi kuzatilmaydi. Agar omborxona yakkaxon bo'lsa yoki boshqa usulda qo'llanilsa, jarayon o'ldirilmaguncha omborxona yo'q qilinmaydi. Bu faqat tizimga resurslar kerak bo'lganda yoki foydalanuvchi ilovani qo'l bilan o'ldirganda sodir bo'ladi. Agar omborxonada ViewModel-da qayta qo'ng'iroq qilish haqida ma'lumot bo'lsa, ViewModel vaqtincha oqadi

Faoliyat tugadi, ammo ViewModel hali ham atrofida

Agar ViewModel engil bo'lsa yoki operatsiya tezda tugatilishi kafolatlangan bo'lsa, bu oqish katta ahamiyatga ega emas. Biroq, bu har doim ham shunday emas. Ideal holda, ViewModels-da ularni ko'rishda biron-bir ko'rinishga ega bo'lmaganda bepul borish kerak:

Bunga erishish uchun sizda ko'p imkoniyatlar mavjud:

  • ViewModel.onCleared () yordamida ViewModel-ga qo'ng'iroqni orqaga qaytarishni omborga aytishingiz mumkin.
  • Rezervuarda WeakReference-dan foydalanishingiz mumkin yoki siz Voqea avtobusidan foydalanishingiz mumkin (ikkalasi noto'g'ri ishlatilishi mumkin va hatto zararli deb hisoblanadi).
  • Repozitoriya va ViewModel o'rtasida aloqa o'rnatish uchun LiveData-dan View va ViewModel o'rtasida LiveData-ga o'xshash tarzda foydalaning.
Ketma-ket holatlar, oqish va uzoq davom etadigan operatsiyalar sizning arxitekturangizdagi holatlarga qanday ta'sir qilishi mumkinligini ko'rib chiqing.
The ViewModel-ga mantiqni qo'ymang, bu toza holatni saqlash yoki ma'lumotlar bilan bog'liq muammolarni saqlash uchun juda muhimdir. ViewModel-dan qilingan har qanday qo'ng'iroq so'nggi qo'ng'iroq bo'lishi mumkin.

Repozitoriyalarda LiveData

ViewModels va qayta qo'ng'iroq jahannamining oldini olish uchun saqlanadigan omborxonalarni quyidagicha kuzatish mumkin:

ViewModel tozalangandan so'ng yoki ko'rish muddati tugagach, obuna o'chiriladi:

Agar siz ushbu yondashuvdan foydalansangiz, kutish mumkin: agar siz LifecycleOwner-ga kira olmasangiz, ViewModel-dan Repository-ga qanday obuna bo'lasiz? Transformatsiyalardan foydalanish bu muammoni hal qilish uchun juda qulay usuldir. Transformations.switchMap sizga boshqa LiveData nusxalari o'zgarishlariga reaktsiya qiladigan yangi LiveData yaratishga imkon beradi. Bundan tashqari, kuzatuvchiga hayotiy tsikl to'g'risidagi ma'lumotlarni zanjir bo'ylab o'tkazish imkoniyati beriladi:

Ushbu misolda, trigger yangilanishni olganida, funktsiya qo'llaniladi va natija pastga yo'naltiriladi. Harakat repo-ni kuzatadi va xuddi shu LifecycleOwner-dan repository.loadRepo (id) qo'ng'irog'i uchun foydalaniladi.

ViewModel ichida Lifecycle ob'ekti kerak deb o'ylaganingizda, Transformatsiya echimi bo'lishi mumkin.

LiveData kengaytirilmoqda

LiveData uchun eng keng tarqalgan holatlar bu ViewModels-da MutableLiveData-dan foydalanish va ularni kuzatuvchilar tomonidan o'zgartirilmasligi uchun LiveData sifatida ko'rsatish.

Agar sizga qo'shimcha funktsiyalar kerak bo'lsa, LiveData-ni kengaytirish faol kuzatuvchilar borligini bildiradi. Bu, masalan, siz manzilni yoki sensor xizmatini tinglashni boshlaganingizda foydalidir.

LiveData-ni qachon uzaytirmaslik kerak

Ma'lumot yuklaydigan ba'zi bir xizmatni ishga tushirish uchun onActive () -dan foydalanishingiz mumkin, ammo buning uchun yaxshi sabab bo'lmasa, LiveData kuzatilishini kutishingiz shart emas. Ba'zi odatiy naqshlar:

  • ViewModel-ga start () usulini qo'shing va imkon qadar tezroq chaqiring [Blueprints misoliga qarang]
  • Yuklamaga xalaqit beradigan xususiyatni o'rnating [Qarang GithubBrowserExample].
Siz odatda LiveData-ni kengaytirmaysiz. Ma'lumotlar yuklashni boshlash vaqti kelganida, sizning faoliyatingiz yoki qismingiz ViewModel-ga xabar bering.

Arxitektura komponentlari bilan bog'liq boshqa mavzularda sizga rahbarlik (yoki fikrlar) kerakmi? Izohlarda bizga xabar bering.