ah, I found the solution: <https://medium.com/the-...
# android
though in this particular case the delegation doesn't do that much compared to just having the disposable directly in the view model? I still have to override
onCleared
to call the delegate's
clearDisposables
.
c
Author for both articles here 👋🏻 Delegation is certainly optional and it really depends on your own unique circumstances.
i
yeah, noticed your picture in the thread above 😄
it actually works if I give the interface's method the same name (
onCleared
) though that's hacky
c
Depending on how much you're using Rx though, it can make sense to extract a smaller interface over CompositeDisposable, something like
DisposableHandler
, and then that would maintain creating the
CompositeDisposable
and ensuring the correct function is invoked. I used this at a previous company to share code with the Activity, Fragment, and ViewModel. Albeit there is a bit of ceremony going on and you'd still likely end up with a
DisposableActivity
,
DisposableFragment
, and
DisposableViewModel
, but that's one way delegation could play into it.
Having the
onCleared
function also works though, especially if you just want to share it between ViewModels. Happy to hear the articles helped you out, seeing that made my day 🙂
i
yeah thanks! I don't like the idea of "overriding" the
onCleared
function via interface composition or delegates though. The compiler wouldn't detect if the view model's
onCleared
was renamed, for example
and moving the code to a small interface honestly doesn't seem to bring any benefit over just maintaining the disposable directly in the view model? It's about the same amount of code and I can forget calling the interface's clear in
onClear
too
c
Yeah the main benefit is honestly keeping the CompositeDisposable behind a facade so it can be a bit more decoupled, in the grand scheme of things though it usually plays out to being contained in 3 top level classes so also not a ton of duplicated code either
i
agree with the first part. Concerning the second, Im probably missing something. With the interface (and without inheritance) I still need to have in every class using it 1) the val declaration and 2) overriding
onClear()
(or equivalent) to call the interface's method, so it's pretty much the same amount of code than without the interface.
c
So the interface might look something like this:
Copy code
interface DisposableHandler {
    fun addDisposable(disposable: Disposable)

    fun addDisposables(disposables: List<Disposable>)

    fun clearDisposables()
}
Then the implementation (what would be delegated to the Activity, Fragment, ViewModel) would use a
CompositeDisposable
as the property to proxy those. There are some more advanced techniques you could use, such as having
Application.ActivityLifecycleCallbacks
registered to invoke
clearDisposables
when
onDestroyed
is called. There is a similar callback for Fragments too, but I'm unsure if ViewModels have anything similar... That'd be one way to avoid having a base class though.
i
yes, what I mean is that the implementation would still have to call
clearDisposables
on the interface, which would result in the same amount of code than just managing them itself (assuming usage of
CompositeDisposable
)
ActivityLifecycleCallbacks
would probably improve this though.
c
Yeah, it's very much on the fringe of overengineering. It's one of those things that I wouldn't necessarily push for but I also wouldn't be against if it were there