Issue
I'm new to making android apps, Kotlin, and just trying to get my head around the MVVM design pattern.
I'm attempting to make a login screen while also integrating well with my team's existing code. Making the login screen work went well until I noticed that I was running into life-cycle issues with uninitialized lateinit vars (even though the code definitely ran the initialization statements) like SharedPreferences or the username and password fields etc.
After reading up more on MVVM, I believe that the existing code which I was learning from (which contains lateinit vars for Context, the Fragment, and View within the ViewModel etc) is fundamentally flawed and fails to decouple the ViewModel from the View life-cycle.
However this has me confused. To my understanding, the ViewModel is supposed to contain the business logic and any data which we want to survive configuration changes. On the other hand, the LoginFragment should only contain UI and OS interactions such as displaying the View or capturing input.
The LoginViewModel only contains code interfacing between the elements of fragment_login.xml and SharedPreferences, or logging errors:
resetFields(): empties the fields to blank
onLoginButtonClicked(): just calls the Retrofit function to POST the username/password a server for authentication
onLoginSuccessful(): saves the data to SharedPreferences
onLoginUnsuccessful(): changes the field's error message and logs the error
Because I used DataBinding on the xml elements, nothing (as far as I can tell) needs to be independent of the life-cycle (or rather, several things require access to the context or fragment!).
What is the proper way to go about this? Currently I am thinking that the ViewModel simply shouldn't exist and that all functionality (of which there is very little) should actually just be within LoginFragment). I was considering learning about and using LiveData next, but I just can't see how LiveData or ViewModel are necessary in this situation.
Solution
The main goal of any architectural pattern is to achieve Decoupling, Single responsibility and restricting Anti Patterns, to be precise code should be more readable, scalable and easily testable. I know in some instances using this patterns might seem redundant for your use case, but always keep scaling in mind when ever developing even a simple feature. This will pay off in long term and help peers understand and isolate code better.
In Android, always remember view or UI(Activity/Fragment) should be as dumb as possible, only responsibility of them should be to listen to user touches and display data, by doing so you can test all your logic in isolation without relying on Android Framework.
MVVM is once such pattern designed keeping pain points of Android in mind, it does not cause any harm using it when needed to delegate even simple tasks like storing data to preferences, minor transformations to data before displaying. Let's say you have a static page which just displays static data using String and nothing else then you can avoid ViewModels.
MVVM pattern does not enforce you to use ViewModel for every Fragment/Activity, it recommends using it when needed as a best practice, ViewModel is just a data holder which persists configuration changes.
Answered By - Rajan Kali
0 comments:
Post a Comment
Note: Only a member of this blog may post a comment.