Modularization is not a new concept in software development. Modular programs were created in times when most of us were not even in this world yet. Although this kind of software design is a quite old technique, its implementations have been evolving throughout decades resulting in number of great inventions. In the AEM world we also have the ability to create modular applications as AEM is built on top of OSGi – a framework which is designed to support modular systems. And it works well. Pieces of functionality are gathered into logical units called bundles, they communicate with other bundles through clearly defined interface (OSGi services). Developers working with AEM on daily basis know that perfectly.
However, AEM-based applications are often very complex systems providing not only pure CMS capabilities, but also consisting of multiple integrations with other systems like room booking, real-time stock market data, identity management, federated search, etc. Thanks to OSGi modularization, you can implement all of the integrations as separate modules and run them all on an AEM instance. Such an approach seems quite natural for AEM-based systems - everything is deployed into single AEM instance and if your system expects more traffic you can scale it horizontally by adding another instance. Simple and it works. At least in theory.
In practice, we can often observe that some parts of a complex system are used much more extensively than others and require far more resources. Scaling of such a system may be challenging since the only option we have is to add another AEM instance. Unfortunately, this is not an easy operation, especially if you don’t use MongoDB setup. Additionally, it may generate significant costs on infrastructure and licencing. As a result, even if a system is designed to be modular, from scalability point of view it’s still a monolith - particular parts of the system can’t be scaled independently. So how can we deal with such issue?
If we think of highly-scalable enterprise systems it’s worth considering moving from AEM-based design to microservices architecture. In this approach, some bigger logical parts are deployed separately, outside of AEM – all of these parts are called services. Of course, AEM is still there (it’s another service) and plays one of the most important roles - it delivers the user experience, i.e. websites, pages, their layout and static content. Most of the dynamic content though, is provided by other services deployed e.g. as a stand-alone applications on Tomcat or Node.js servers. The assembly of pages served by AEM and the dynamic content from other services is done with use of… another service. Sounds complicated? Although from deployment point of view it’s more complex than simple AEM-based approach, it brings a couple of significant advantages:
- Improved scalability – each service can be scaled separately. If you expect a lot of traffic and the majority of processing is related e.g. to search, then you can add another instance of search service only. You don’t need to replicate the whole system.
- Easier deployment – since the services are independent you can upgrade each of them easily whereas other services remain untouched.
- Faster development – you are not limited to OSGi technology, so you can develop each service with solutions which best suit the service needs.
- Reduced cost and time-to-market – thanks to above, the overall cost of change implementation and time needed to deploy it to production is reduced significantly
An example microservice architecture is depicted on a diagram below. If you want to know more on how microservices in AEM world work in practice, please join my session at the AEMHub conference, starting 8th of September in London. I will show you how this approach can be implemented and what benefits it brings.