Hi all. I have a question about MVVM architecture....
# android-architecture
j
Hi all. I have a question about MVVM architecture. Is there an apparent disadvantage to it?
Tbh I was asked this in an interview and I couldn’t come up with anything and we just discussed about how it does not have reference to the view and how sometimes one would add a livedataevent to handle simple clicks from the view to open a new screen.
c
Depends on what they’re comparing it to. It has some overhead, which may be more or less than the alternatives considered in the interview.
o
@jayeshsolanki93 MVVM architecture by itself? Or implementing MVVM on Android? The ViewModel not having a reference to the view is not a disadvantage, that is one of the pro's. This way only the V in MVVM is framework dependent. Also no need for using livedata for events. I believe LiveData is built for showing state, events aren't states. Use Coroutines Flow for events.
All in all, I'm curious if those arguments were made by the interviewer or by you during the interview?
a
LiveData and Flow are fine for events, imho. With LiveDate you just need to implement SingleLiveEvent
🚫 1
👎 2
s
I do have one thought, although not directly related to what MVVM is, but how I mostly see it implemented.
ViewModel
in my opinion does not have a view reference in it for a reason, that it is not bound by a view. I have an issue with how most applications I see have one
ViewModel
for each
View
in the architecture. That just makes it a presenter without a view reference. In my opinion, a
ViewModel
should be reusable, by any view that wants to show the data that a particular
ViewModel
exposes.
But by coupling it with each view, i.e, having
HomeActivity
with
HomeActivityViewModel
. We hinder that reusability part of it. The part of the issue is how even android studio suggest you to create
Fragment + ViewModel
through it's wizard.
1
o
@Saurabh I think it is normal for there to be both reusable and non reusable, usecase specific viewmodels. HomeViewModel should be okay, but it can reuse exposing some view states, such as button state etc.
s
@Orhan Tozan I don't disagree with you. But if you think about it, a non-reusable ViewModel is just a presenter. I agree that it still doesn't have a view reference, but by coupling functionality, you can't use your ViewModel anywhere else.
o
I never used MVP myself, but from what I know is that Presenters are differnet in viewmodels in that viewmodels represent the current state of the view, while presenters do things more imperatively. E.g. in a login form, viewmodel would expose usernameTextInput: LiveData<String> to let the view know the current value of textfield, while the presenter in that case doesn't do that
s
Yes you are absolutely right about how the data is driven in the case of both viewmodels and presenters. My case here is that since we already have separated out the view from the viewmodel, why couple it with functionality of a single view. I think we can achieve much more effective reusability if we don't do this.
d
SingleLiveEvent is an Anti Pattern. The correct tool is some kind of stream that can be subscribed to.
Flow
is good for this.
.NET has the best implementation of MVVM IMHO. I encourage all to look at it.
A strong emphasis is put on Events and Commands in the .NET MVVM.
But MVVM is not an architecture, it is just a pattern that is part of the solutions overall architecture.
a
If trying to answer the question there is no "apparent" disadvantage to MVVM itself. If you read articles on these architectural pattern they always conclude MVVM is the most "advanced" variation of a layered architecture vs MVP and MVC which had an apparent disadvantage of tight(er) coupling with View
u
If you stop thinking about ViewModels as special, the big picture will start to make more sense. What we call viewmodels are just (usually) screen scoped components. Not different from some other domain logic object, which just happens to live in a wider (app) scope
only difference is scope it lives in, which should be transparent
a
You can get a decent answer on this just google "mvvm pros and cons". The first disadvantage for me that came to mind was sometimes very simple things can seem overly complex but this is kind of true for any real architecture. Displaying a toast for example, its easy to just have the VM do it but that is incorrect, you need to use some sort of single event mechanism and the obvious choice was even stated in this thread is a bad idea and your left not knowing what to do. In practice a lot of similar things come up where you know how to do something, just not with MVVM even though you are stuck using MVVM... which is still the best in my opinion.
o
IMO the saying "there is no such thing as a perfect system" holds true here. Typically with MVVM you have your view (activity/fragment), VM (obvious) and a repository (or w/e you call it). VM is suppose to be where you hold state + business logic. the view should be very minimal. And your repository is where you do your networking/data layer logic plus maybe mapping of data model -> UI model. But what happens when you start throwing all your business logic into a VM? It ends up being very similar to the old days where you just kept everything in a single activity/fragment file. Typically you will hear, well create another presenter or something similar to break down the logic in your VM... And for me that's where it gets confusing. What's the point? The other is VM, at least in Android world, doesnt work well with single events. I know there's a bunch of ways to handle single emitted events, but it just doesn't sit right with the idea of VM on Android. The whole point is for the VM to hold data that that doesn't get destroyed and recreated like your view, which can happen for many reasons, so that the data is preserved and immediately ready without having to load again. And again we say VM serves the purpose of state + business logic. Well it doesn't fit 100% with actions that are taken only once or events that are supposed to only happen once. I probably over explained that a ton but I'm like on my 6th today and I'm currently running in place 😂😂😂😂
😅 1
a
I think VM is fine on Android. When it gets "fat" it is an issue buy I think you should have an Interactor/Use case along with Viewmodel so you can have presentation logic in VM and business logic in the Interactor
o
@Anastasia Finogenova yes exactly. When it starts getting polluted is when I scratch my head a bit. Also another thing that comes to mind and what I ee on projects I work on is the disagreement between if the the VM should be bound to a specific view or if it should be built in a way where it can be reused by any view, which ultimately might mean there might be some "business logic" in your view layer.
a
I don't understand how it can be reused if it holds specific presentation logic to that screen. I am for single responsibility principle If there is a need to share state in between your screens you can have a single shared Viewmodel. That is the recommended way to communicate between Fragments now for example. But why would you want to reuse it for every view? You can potentially have a base Viewmodel if you have generic logic to provide to multiple views that you are going to inherit from (I have seen that) or you can create extension funs to be used across multiple VMs as an option too
If your concern is code duplication so you try to have one ViewModel
o
Well let's say you have a view that has state which is driven off of data from API #1. And two other views which also have their UI driven off of data from APi #2 and #3 respectively. And let's say you have a bunch of flags that come down from API #4 that drive the state of a common toolbar component. And let's say you have three activity views which all should follow the same logic for their toolbar but they all show different ui components. One way to go about it Is creating a single viewmodel to be used for the toolbar business logic. And a different view model for each activity that holds the business logic for the rest of their UI. And then second approach is you have just a total of 3 VMs, 1 for each activity, which may hold redundant business logic for the shared toolbar component. This is just a quick idea I came up with that I think may paint the picture I'm trying to describe... Not sure.. 🤔
Updated/edited my comment to be more clear
I prefer the first approach, where each activity would have a total of 2 VMs. One for the shared toolbar and one for their own UI. But I come across some folks who try to follow the single VM -> single view approach since that's what it looks like in common Android tutorials/code labs/documentation.
a
I think single view + single VM is just a simplification in the tutorial
👍 1
o
Yes I agree.
a
There can totally be one shared ViewModel If there is a case for it. But in now if you follow the single activity pattern such thing as a toolbar logic can reside in your activity VM
o
Yes absolutely 👍. I think we are probably saying the same thing. I was just trying to bring to light the argument/debate that I get/see often when it comes to what logic should live in the ViewModel.
👍 1