Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Modern Android Development Using MVI Architecture

Modern Android Development Using MVI Architecture

Over the past years, app architecture has evolved. From god activities to MVP to MVVM which became popular after Google announced Android architecture components to MVI. the latest in the MV* band.

Jetpack compose, the modern UI toolkit for Android introduces a new way of writing your App UI. It is declarative. Hence, compose works fluently with unidirectional data flow architectural patterns.

In this session, we’ll see how the common architectural patterns work with Jetpack compose paradigm. We’ll go through the Model as the single source of truth. We’ll also look at handling SingleLiveEvents and app navigation using MVI pattern, and the benefits of unidirectional data flow. In the end, we’ll have fewer UI - related bugs in our Android apps.

Beatrice Kinya

October 25, 2022
Tweet

More Decks by Beatrice Kinya

Other Decks in Programming

Transcript

  1. MVP - Model - View - Presenter - Model is

    just data. - Presenter fetches data from the model, and manages state of the view. - It takes action based on user input in the View. - It calls methods on the View to notify it of state changes. - View receives method calls from the Presenter to be notified of changes to update itself.
  2. MVP CONT’ - Presenters have a reference to the view.

    The view ia usually an activity or fragment injected into the presenter as an interface. - The presenter call functions on the interface to update the UI. - Composable functions do not have a return value. Hence, no view references to pass to our presenter. - Making MVP less ideal for Jetpack compose projects.
  3. MVVM - Became popular when Google announced AAC: ViewModel, LiveData

    etc. - ViewModel is the link between the View and Model. - ViewModel stores and manages UI related data in a lifecycle conscious manner. - Model is data mapped into observable fields like LiveData, or StateFlow. - When there are changes in the model, the UI observes the changes and recomposes itself based on the new data.
  4. MVVM - Instead of updating the view imperatively like in

    MVP, MVVM uses observable data types making it a unidirectional Data Flow architectural pattern. - Downside: multiple objects for different UI states.
  5. Model - In MVVM, model is just data e.g. A

    list of movies - In MVI, model represents state. - It tells the view what to display E.g. Loading, Data, Error. - When the model changes, the view gets notified and recomposes itself using the new state.
  6. Intent/UI Events - An action that changes state e.g. user

    fetching favourite movies from an Api - MVI pattern uses redux style to create new state. - There are three components: - State - state holder - Action - Command to change state - Reducer - a pure function that takes the previous state and action and creates a new state
  7. Reducer - Reduce function directly in the ViewModel OR -

    Separate the reducer from ViewModel - Reducer will be responsible for holding and processing state - ViewModel will be responsible for presentation layer business-logic, and transforming events from the UI layer into Intentions passed to the Reducer.
  8. View - UI i.e. a composable function. - It listens

    and responds to state changes. - Publishes stream of events as they happen to the ViewModel.
  9. Time Machine - Optional feature. - It saves all states

    during a session. - You can do with it as you want: log to crashlytics, display in a debug menu or a screen where you can check all the steps made previously. - Note: Consider not to implement this by default. You’ll have chatty logs. Just use it for debugging purposes
  10. Handling Configuration changes - The UI will display the most

    recent state. - However, remember to save state object. - Use - ViewModel to handle configuration changes like screen rotation - ViewModel saved state module to handle process death - Any other state saving mechanism
  11. Single Live Events - E.g. Showing a snackbar message. -

    During configuration changes, the app will use the latest state. - It’ll show the snackbar again, which is not so good. - There are several ways to handle single live events - Sending ViewModel events to the UI - Google recommendation - Using Kotlin Channel Sample project: https://github.com/BKinya/Calculator-App
  12. Navigation Options: - Making navigation be part of our state

    - State should hold data the app should show on a screen - Handled as a side effect. - But side effects are related to API calls, database access, remote logging - Call navigation directly from the UI. My preference.
  13. Wrapping Up - Improved state management. - The “planning” effect.

    - Unidirectional/Cyclic Data Flow. - Immutability, hence single source of truth. - Debuggability with time machine. - Testability.
  14. Downside - Lot’s of boilerplate code. - Each view will

    at least have a model, intent and a reducer function. - For large projects, this is a non- trivial organisation problem. - Solutions: - Use Android studio template support - Implement base interfaces - Modularisation
  15. Resources - Sample project: https://github.com/BKinya/Movies-App - Reactive Apps using MVI:

    http://hannesdorfmann.com/android/mosby3-mvi-1/ - MvI, a new member of MV band: https://proandroiddev.com/mvi-a-new-member-of-the-mv-band-6f7f0d23bc8a - MVI - the good, bad and ugly: https://adambennett.dev/2019/07/mvi-the-good-the-bad-and-the-ugly/ - State and Jetpack compose: https://developer.android.com/jetpack/compose/state - State holders and state production in the UI layer. https://www.youtube.com/watch?v=pCX9wvu-Bq0