dotanuki-labs / norris

An app that existed before Android existed! 🔥
MIT License
470 stars 38 forks source link

[QUESTION] Domain + UseCase + Livedata #2

Closed MayconCardoso closed 5 years ago

MayconCardoso commented 5 years ago

Hey there! First of all, congrats on the job!

A have a little question about architecture stuff. How would you handle with some observable use case (RxJava or LiveData) on the domain layer?

For example, there is some service updating the data on Room Database, those updates must be sent to the UI.

So basically we have ViewModel connected on some UseCase that is observing the Repository that is observing a Room query.

How would you do these kinds of connection between the layers once the Domain layer is an only Kotlin module, without android dependencies?

Thanks!!

lcszc commented 5 years ago

Accordingly to the description of this project it has no plans and does not wants to use LiveData. This project uses Kotlin Flows to ensure the power of Kotlin.

If you still wants to use LiveData you can use it on your presentation layer. Let your domain free of that thing.

You can also read the README of the project because it explain a bit of how it works and what it uses.

MayconCardoso commented 5 years ago

I've been studying a little bit about unidirectional data flow since I opened this issue. I had heard about UDF but I had never looked at some project using it before. I would say I was a little lost at first I saw this project. But now, I got it.

@itscorey thanks for the answer!

lcszc commented 5 years ago

It is a bit complicated, but is something really nice to learn and use. I think the main goal of this project is to share how we can use UDF.

May the author of the project can explain it better to you.

Also, do not worry, you can use whatever you want (LiveData) in your project. If you do use LiveData, just use it on your presentation. Thank you.

ubiratansoares commented 5 years ago

@MayconCardoso LiveData is just a simple and lifecycle-aware implementation of the Observer Pattern

(and by "Lifecycle" here, you should understand the Activity's lifecycle, for instance)

As @itscorey correctly aforementioned, this project does not use LiveData, simply because I'm pretty sure that we don't need it. Despite the fact that I particularly believe that LiveData is a bad abstraction - once it is coupled on the Android's UI thread - the real thing is : Coroutines + Flow has* all you need, because

Regarding to your question :

For example, there is some service updating the data on Room Database, those updates must be sent to the UI.

Just use suspend from your data layer to your ViewModel layer. If you want to decorate one invocation of a given suspend with two or more states (like Loading, Success, Done, for instance) my suggested approach (as you might check in the project) is to use a StateMachine like abstraction; this is not the only option, though. Implementations of the UDF style out there will call such abstraction by Reducer and other names.

If Room can output a DB operation in the suspendable way - like Retrofit does nowadays - you have everything you need; otherwise, you can wrap a Room DB operation in a suspendable operation. This project has as an example of this kind of wrapping, leveraging suspendCoroutine utility.

Hope I could clarify a bit your questions.

MayconCardoso commented 5 years ago

Excellent explanation of both of you! Thanks, guys for the help! I'll keep studying coroutines. I am used to using RxJava and I had never used neither coroutines nor its flow approach.

You can close this issue if you want to!

Thanks