Sponsor: Do you build complex software systems? See how NServiceBus makes it easier to design, build, and manage software systems that use message queues to achieve loose coupling. Get started for free.
What is vertical slice architecture and how does it compare to clean architecture? Ultimately it’s about coupling and dependencies. With vertical slice architecture, you’re organizing your code across a feature rather than layers. The focus is on features and capabilities rather than technical concerns. Coupling is limited by the scope of the feature and the size of the vertical slice.
Check out my YouTube channel where I post all kinds of content that accompanies my posts including this video showing everything that is in this post.
Before jumping into Vertical Slice Architecture let me first talk about Clean Architecture and use it as a comparison. In Clean Architecture (or Onion, Ports & Adaptors) the main aspect to point out is how dependencies point inward.
The core of your application described as “entities” in the diagram above is what contains your core domain and business logic. It has zero dependencies on any web or application frameworks or logic. The focus is purely on business logic or domain model.
As you go outwards the “uses cases” layer contains your application logic and will invoke your core domain or “entities”. It doesn’t matter how you term these layers or what they contain really, the gist is that dependencies point inwards. The outer layer will depend on the more inner layers.
Put simply, it’s about coupling. Check out my post on coupling and I cover Afferent and Efferent Coupling.
Vertical Slice Architecture
There are many different strategies for dealing with coupling. Vertical Slice Architecture is just another but handled differently. Instead of separating based on technical concerns like Clean Architecture, Vertical Slices are about focusing on features.
This means you’ll take all the technical concerns related to a feature and organize that code together.
Think about a cake that has multiple layers. Now cut a piece out. It’s a vertical slice.
By doing this you’re dealing with coupling in a different way because slices are for the most part, self-contained. They don’t couple to other slices.
I said that they are self-contained, however, features obviously are going to relate to the same underlying domain. In this case, features may share an underlying rich domain model. They may also share an entry point such as a web framework and host, for example, ASP.NET Core. However, everything you’d typically think of being in separate layers in a Clean Architecture (all data access, validation, authorization) is kept together in a single feature. They aren’t separated by different projects.
To illustrate this more, maybe some features are invoked by a web framework and some are invoked by a message processor picking up messages off a queue. There can be some features that share a domain and some features that just have straight data access and use simple data models in more of a transaction script style.
What this looks like in code is having files for various features live alongside each other. Again organizing code by feature, not technical concerns. In the YouTube video, I re-structure a Clean Architecture towards Vertical Slice Architecture. Ultimately you end up with an organization similar to this.
Here are the contents of the GetMyOrders.cs. It contains everything required to get the list of orders.
You may be asking: “why aren’t you using a Repository or why isn’t the data access abstracted”. The reason is that there’s no need to abstract it into anything else. This feature is about returning this specific result set and shape of data. In the prior version, a repository was being used to return an Aggregate, which ultimately was fetching more data than what was required. Simply go to the source and get the data required to build a result.
You may also be asking, “But what if you need to replace Entity Framework”. Then change the dependency in this feature. You’re defining dependencies for a single slice. If the overall schema changes that end up affecting multiple features, then you’ll end up changing those features together. In my experience that won’t be a large number if you actually needed to change the dependency.
Things that change together (features) belong together. That’s what Vertical Slice Architecture is about. Stop focusing and organizing by technical concern but rather start focusing and organize by the features and capabilities of your system.
Developer-level members of my CodeOpinion YouTube channel get access to the full source for any working demo application that I post on my blog or YouTube. Check out the membership for more info.