A few weeks back at our monthly #PETechtalk for Deloitte Platform Engineering, I spoke about "Hexagonal Architecture" and how exploring the past can help us to build our future. I promised those who attended I would follow up with a blog article giving you the highlights we went through and also provide some of the rich and useful resources that I discovered in putting this presentation together… and so here it is.
Nostalgic Look Back
Having been in the industry since the '90s, it was very nostalgic for me to look back to the way we developed software in 2005 and how something like "Hexagonal Architecture" has stood the test of time. Often attributed as being the foundation for the modern Microservice Architecture we use today(ref 1),(ref 2), those credited with its inception have been involved in some of the most influential changes our industry has seen in the last 20 years.
What is Hexagonal Architecture?
Colloquially this term has been used to describe 3 different patterns, each of which built upon (and gave credit to) the architectures that preceded them:
- Alistair Cockburn's "Ports and Adaptors" pattern in 2005
- Jeffrey Palermo's "Onion Architecture" pattern in 2008
- and Robert C. Martin's "Clean Architecture" pattern in 2012
While each of these patterns has a different focus, the taxonomy of this architecture can be seen through 3 distinctive attributes that appear across all of them:
- Inside/Outside – A hexagon or set of concentric circles that separate the inside application from the outside infrastructure
- Primary/Secondary sides – An asymmetrical delineation between the user-side (what drives the application) from the data-side (what is driven by the application)
- Ports – Interfaces that are independent of both application and infrastructure, which define the functionality that is implemented in the form of “Adaptors”
From this structure we can summarize 4 key features promoted by the architecture:
- Dependency Inversion –The externality of the interfaces naturally inverts the dependencies, decoupling components, supporting modularization, and allowing them to be tested in isolation
- Separation of Concerns – The application is divided up into concentric circles, where each layer can only know about the layer beneath it, creating a separation of concerns for each layer.
- Domain-Driven - The application is now agnostic of technologies and infrastructure and can be built and tested long before any decision is made on which technology to use
- Clear Delineation – Allows for clear identification of what is application or infrastructure, and what adaptors are drivers or driven.
Putting it into practice
Looking at this architecture can often be daunting, and indeed implementing a purely hexagonal application does require a lot of discipline and care. There are however easier ways to put this into practice by picking your battles and choosing when to adhere to these principles and when not to.
An example of this would be to combine the Mediator pattern with dependency inversion and use the System.CompositionModel.Composition namespace (previously known as MEF) to dynamically load observers as adaptors into your solution.
Imagine a report generator that may have a variety of different technologies it could use to report its data, perhaps you can output to PDF, or Microsoft Word, or even HTML.
Without the use of hexagonal architecture, your report generator would be dependent on all these technologies at the same time, and any updates to one would require updating the entire application.
By putting each of these technologies into separate adaptors you isolate the technology to the outside, which frees up the report generator to now be tested in complete isolation, agnostic of any of the technologies being used.
Your report generator now “drives” the adaptors to perform its task, making it more modular and supporting better maintainability. New adaptors can be created without needing to update or deploy the entire application.
Whether you are interested in implementing the architecture in its entirety, or just making good use of some of the principles that it promotes, looking back at how these architectures came about can often provide a great wealth of knowledge to help us build our future.
Projects using Hexagonal Architecture
If you want to look deeper into this architecture from a practical standpoint, several projects can be found on git hub to support this:
|Java||Tom Homberg||Example implementation of Hexagonal Architecture|
|C#||Ivan Paulovich||Acerola: Hexagonal Architecture|
|PHP||Brian Webb||Hexagonal Laravel Architecture|
|Python||Sebastian Buczynski||Implementing the Clean Architecture|
Here is some additional reading which you may find useful. If nothing else I would recommend you check out the YouTube video “Hexagone” which is the only record of Alistair Cockburn lecturing on his original Ports and Adaptors pattern.
- Use of the Hexagonal Architecture Pattern
- Another story about Microservices: Hexagonal Architecture
- Alistair in the “hexigone”
- Implementing a Hexagonal Architecture
- Think Microservices: Hexagonal Architecture