Programming WTF: Clean Software Architecture Use Cases - WHAT, WHY, WHEN w/ Code Examples

Video Statistics and Information

Video
Captions Word Cloud
Reddit Comments
Captions
okay um and these are some high-level questions I'm getting today some complicated questions almost knocked my tower over okay this is not beginner this is not a beginner question but I'll do my best here I not sure what your skill skill level are panas but just for the beginners watching this some of this some of this might go over your head but I'll try and explain it simply it's the questions I wanted to ask what are these use cases use case classes exactly I mean what's the true purpose of using them with repositories and clean architecture so if I into really like there's a couple there's a couple purposes so let me try and break it down like this so two two main purposes in my opinion so geez I can't spell here two main purposes so design phase so I'll try and write some of this out so when you are building a new app or refactoring an old app use cases are essentially a represent representation of what your app must do in order to work properly these can be arrived at through problem domain analysis so we're talking user stories and problem statements so let me link I can't explain problem domain analysis in too much detail because it's a little complicated it just takes a while to explain I'm gonna paste an article into the chat which talks about this so um let me give you a practical example from the project I've been working on lately so this is paws trainer and in the domain package or the domain module you will find so this is a multi module project you will find three packages here domain model you might also other people might call this entity but the word entity is very confused in my opinion but we have these domain models so this is just like a data container class which has no third-party frameworks then we have our repository interfaces but not the implementations of the repository so we have get alarms we have an alarm repository and alarm service and it's supposed to do these particular things set an alarm cancel alarm dismiss alarm and then we have these use cases here so we're talking cancel alarm delete alarm dismiss alarm get alarm you get the point set alarm updater create alarm all the things my app my alarm app needs to do so why is this called domain because I actually wrote that domain layer before the back end and the front end so I kind of think of the domain layers like a middle module it's between the back end and the front end the presentation domain data it's in the middle and I wrote it by performing problem domain analysis if you want to understand what I'm talking about here there's there's a good photo problem domain that's a good one the way you do program problem domain analysis is you I said what does the program do and yeah go read that article if you're curious so bye so I literally like pen and paper or in notepad will write out I'll do my problem domain analysis before I decide what database I want to use before I decide what the user interface looks like in this case I'm refactoring an application so I already kind of have some ideas about what the user interface looks like and so forth so I go from problem domain analysis written down in plain English to building my use cases and my what I call a domain models sometimes people call this an entity what do these things look like so here's okay so what I'm just explained here is that I'm able to design what my application does and the data it needs to represent so an alarm app represents an alarm in a high-level abstract way so that's the what I was talking about here so it helps my design process because I can reason about what the application will need to do and the data it will need to represent without writing any Android code without writing any back-end code without writing any front-end code so if I was building a new application I would start by building my domain layer if you're doing single module you can make like a domain package and put your use cases there in this case I'm building an application which needs to work with both iOS and Android and the iOS app and the Android app we'll both talk to the domain layer module sorry okay so that's one of the purposes then there's a second purpose so this is let me since we're just quoting quoting Uncle Bob left and right here coordinating no I can't you I'll paraphrase Uncle Bob so this is the runtime Faye's so when the app is actually running what does it do it coordinates the I hate this term business logic of the back end so then we're thinking repositories so instead of verbally explaining this too much let me show you the code so now here's the thing sometimes the domain layer isn't really that useful in a single module strictly app strictly Android application so let me see if what would be a good one you had lead alarm so if you're doing a simple application so maybe like a note-taking app and the calls to your repository are pretty simple so we're just saying like repository dot delete alarm in this case there's not actually a lot of benefit oops - having a use case because as you can see here all this use case does is it just basically provides an extra layer of abstraction over a repository which should be an interface which is generally abstract enough so when I show you that you might think okay well what's the point then once you start to have more complicated business logic I hate that term that's when we start to see the benefit so let's look for example at a more complicated use case so here we're all we need to do in this use cases we're just saying delete an alarm from the repository this interface is in the domain layer so I can write all of this out without even encoding the actual repository implementation that which implements the repository and I can test it I wrote this domain layer using test-driven development as you can see you will find tests here not for the really simple ones but for the more complicated ones when we have more complicated business logic I I can't think of a better term but yeah whatever that's when we start to see the value of the use cases where's the where's a good one this is a good one okay so this is where use cases really start to shine at runtime so now all of a sudden we're not just making one call to one friggin repository but in this use case let me talk you through it so in our alarm application I have to store an alarm in a database and I have to tell the alarm manager to do things with that alarm so when the user let me just show you when the user toggles an alarm here you can see there's an on/off switch so I'm just gonna hit on okay so we've set an alarm when the user does that we call our let's say we're dismissing the alarm so I hit it again and then it turns the alarm off when that occurs we need to not only tell the alarm manager which is what is behind the alarm service to cancel the alarm so that it doesn't go off so not only are we telling the service to cancel the alarm but if it successfully cancels the alarm then we take that same alarm and we write it to the database our repository except we set is active to false is active is just whether the alarm is active or not it's very simple so this is kind of what I'm talking about when I say business logic instead of trying to verbally define that term but this is when a use-cases really help you and all very often I will write the steps required in like an itemized list and when I'm writing my tests so this is a test class I'll make sure I write out exactly what I want this thing to do and the different paths that can potentially take so what does that do for us it basically allows us to take this logic this business logic out of our presenter or a front-end logic class so whereas when I used to do for example model-view-presenter just pretend that this thing is a presenter it's a logic class when I used to do this what I would have to do is I would have this thing talking directly to the repository and then it would say to the repository you know dismiss the alarm and then it would talk to the story it would say to the service dismiss the alarm it would basically handle the stuff that you see here the stuff that I showed you it would do all of this manually the result of that is that my alarm or my logic class might present her in my controller whatever was pretty complicated because it had to manage the backend logic as well by having this sort of middle domain layer which is very abstract all I do is I say to this dependency provider remember this is just a way to get ahold of use cases I asked so for example when the user toggles an alarm so on alarm toggled where is that function down here then we'll so if the depending on the state of the switch it'll either say if it's active we want to set alarm if it's inactive we want to cancel alarm or I mixed that up other way around so when we actually want to talk to the back end through the use case I just asked the provider for a use case I give it the data it needs and then I just have one single result to check did it work properly did it not work properly instead of in the same class having this logic here having to check did the service work properly did the repository did the database actually write to the database why the front-end logic class the front-end decision-maker should not care about those things you should pull as much of that business logic out of the front-end logic separation of concerns front-end presentation logic business logic pull them out and that's basically the point of and benefit of use cases so hopefully that was a relatively decent explanation this is not beginner material but that's kind of the main things the runtime it can allow you to abstract out presentation logic from business logic and this will simplify simplify your presenters your view models your controllers your logic classes whatever it'll simplify them but again just understand if you don't actually have like multiple back-end if you just had a database and that's all you're talking to like for example in this one delete alarm all we're doing is we're just deleting an alarm from the repository in this case if that's if you're only ever talking to one repository interface you can actually just skip the use cases entirely and just have your logic class your presenter your controller whatever just have it talk directly to the repository interface if we're just calling single functions so don't necessarily you you don't have to use use cases anywhere everywhere there's one final benefit this is more a benefit of the so this is a benefit of domain layer in general it allows you to have a neutral neutral meaning almost yeah I would say platform independent source of truth for multi plat platform applications so this is only a benefit if you're actually planning on building multi platform applications but we could have so for example as I discussed earlier in the show currently I have one two three four modules we've got Android Data Android app and then I will also have I'll also have iOS app iOS data and what I want you to notice is if I pull up the build.gradle files for these different things so here we have app and then we have Android data I just want you to notice both the Android data depends on common and domain just ignore common for now it's just stuff that is shared across everywhere but notice how it depends on domain and then app also depends on domain I don't think I need to have it depending on Android data so I'll have to check on that I do in the service locator actually so yeah that's fine so yeah that's basically I could probably abstract that I would if I really wanted to but yeah it provides a common neutral ground so if I had my iOS module written in Kotlin native then you would also see implementation project domain and it would use it would make use of the same repository interface and the same primary entity or domain model and so that allows code reuse and abstraction and all that kind of stuff so hopefully that answers your question
Info
Channel: Ryan M. Kay - wiseAss
Views: 3,974
Rating: undefined out of 5
Keywords: Clean Architecture Use Case, Kotlin Test Driven Development, Mockk, Android Tutorial, Use Cases, Kotlin, Android, Clean Architecture, Let's build an app, Android Alarm App, Problem Domain Analysis
Id: WBebmxPExmg
Channel Id: undefined
Length: 17min 55sec (1075 seconds)
Published: Thu May 30 2019
Related Videos
Note
Please note that this website is currently a work in progress! Lots of interesting data and statistics to come.