I'm looking forward implementing vertical slicing, because I also experienced the pain of N-tier kind of layering. However, this doesn't negate the need for clean or onion style architectural layers, because they serve a different purpose - reusability and replaceability of larger architectural/infrastructural/presentational components. From what I've seen so far, the vertical slicing (which seems to be essentially the encapsulation of use cases) goes hand in hand with modern layering techniques, because the command/query handlers can be neatly placed in the core's application layer, just above the domain. This is how Jason Taylor's clean architecture solution template also implements it. But I'm really happy with 'vertical slicing' as a concept; I think it's quite neatly named. It's just a shame to see how common is the misinterpretation of MediatR as 'CQRS'. The fact that the queries and commands are separated is a completely insignificant detail in most cases, and the meat of the pattern is indeed the vertical slicing.
@@FudgeYeahLinusLANdid you try it yourself? How did it go? 😁 I am now at the stage of learning Architecture/Design, and under a few videos asked several people this question. And no one replied 😅
What's the benefit of using CQRS? The same idea can be accomplished by actions in controllers calling "mini services" which contain only one behavior. To me it seems that splitting things into commands, queries and having a dispatcher dispatch events just complicate things. You get a complicated chain of commands if the application is big enough.
I understand where you are coming from. For me, the dispatcher is completely separate from the separation. You don't need it for cqrs. The benefit of separation though improves the single responsibility by moving each 'function' of your mini services into its own class
Since each 'function' may need different dependencies, you don't have these mini services injected with a bunch of depencies that not every function needs.
Great observation! This is where we’re at with some of my companies apps. There is an http layer around a MediatR layer which interacts with an ORM layer. It does provide a level of abstraction so we can independently change the public API from the internals, and the http layer only provides http specific mappings to internal API calls, but it’s just become another N-tier app based on these newer concepts.
@jimmy I'm wondering now with minimal API if the EndPoint just becomes the handler and we can drop the need to use mediatr to service locate a hander for a request so the endpoint becomes the "handler". I guess this won't work will if you want both an API and an MVC app to reuse the same handlers. But, if your project is only an API seems like it would be fine and remove yet one more layer and level of "magic".
You can watch this too from 2 years ago, before covid-19; it's totally the same. I was actually hoping for some differences or updates, but I didn't notice anything.
I never understood why one would create a specific repository for each entity instead of just using the IQueryable interface directly in the service layer. Imho there is no value being added with a repository. Saying that it wouldn't be unit testable otherwise isn't true either. An IQueryable interface is perfectly unit testable. Most ORMs even provide an in-memory database for this purpose.
I completely agree. When you have something as powerful as Linq (where Linq doesn't care if you're querying a database, a collection, a stream...), why not just use it in stead of adding an extra layer of unnecessary complexity? In a previous project I did, we got rid of the extra layer and just used the IQueryable directly to: a) query only the needed fields (immediately hydrating to the class(es) that we actually needed) b) filter / sort / paginate directly without having to go through the entire song and dance of handing them to a repository and letting the repository perform the logic. Using the repository pattern, IMO, only makes sense if you've got extremely complex querying logic that would otherwise need to be duplicated all over the place (which is rarely the case). And even in that case, I'd just create a form of "transformer" that takes an IQueryable and returns an IQueryable where all of the joining logic has already been done. Performance COULD become an issue, but leave that for when it moves from being a hypothetical concern to an actual concern.
Great talk Jimmy! It is great to see how yall are approaching software architecture nowadays. Seeing the evolution in thinking definitely helps to frame what problems these ideas are solving. Is there a sample project somewhere showing some of these techniques?
David Garcia, in addition to Jimmy's GitHub site, for a great example of combining Jimmy's techniques with modern architecture in a practical application I HIGHLY recommend you watch Jason Taylor's video "GOTO 2019 • Clean Architecture with ASP.NET Core 3.0". Jason has good examples on GitHub as well.
I think you went a little bit overboard with splitting code into INPUT -> HANDLE -> RESPONSE. If you think about it, this is what a normal function does. Input are the parameters, handle is the code inside the function and response is what you return. You complained about low cohesion in the layered architecture but instead recreated it inside your vertical slice by doing things this way. Splitting the code into queries and commands is good, since commands and queries will most often have different dependencies. I think you should have kept the layered architecture and just splitted your code this way instead. There is nothing forcing you to use the same dependencies between the commands/queries. My guess is that your failure with the layered architecture comes more from the difficulty of identifying and splitting your code into separate bounded contexts.
03:20 shouldn't use web forms aspx since 2015? lol, my uni to this day still teaching *Web Development* with only aspx web forms and code behind with zero OO concept.
The idea of architecture is very interesting, but for now I will not consider it for use in my projects. Loved Jason Taylor's Clean Architecture concept
Jason is simply using and applying this concept from Jimmy. It is the exact same thing, which Jimmy blogged about and coined the term (Vertical Slice Arch) around 6 years ago.
1. Is I/o buried in the handler or always injected? 2. Testing the implementation details really sounds like wasting a lot of time. You really lost me, when you said you wanted to go quickly over testing and in addition show this in my humble opinion poor testing Szenario. This would all make sense to me, if you would Unit Test the handlers. Anyways, great inspiration and great talk, though not the silver bullet I hoped for for the reasons explained above.
John, I deleted my original comment because as the video progressed I liked Jimmy's ideas on unit testing better than mine. I unit test my CQRS handlers and domain classes, and rely on a few integration tests to make sure the vertical slices are healthy. Jimmy espouses skipping the unit tests on the handlers and relying on the vertical integration tests to test them. Really it seems like either approach should be fine. Because I implement all I/O in infrastructure assemblies I use interfaces in the application layer and inject the I/O implementations with .net Core's built-in constructor dependency injection. Ever since I discovered Jimmy's CQRS with MediatR pattern a few years ago I've been in love with it. For a great example of combining Jimmy's techniques with modern architecture in a practical application I HIGHLY recommend you watch Jason Taylor's video "GOTO 2019 • Clean Architecture with ASP.NET Core 3.0". Jason has good examples on GitHub as well.