Micro frontends are rising in popularity, and for very good reasons. If you are not aware what micro frontends are, I would suggest reading this article.
I’ve been working with micro frontends for almost 2 years now, and love working with them. The greatest advantage in my opinion, is that they increase ownership. Most micro frontends are split up according to the domains of an application, where one team is responsible for one specific domain of the website (for example, team products, team account, team checkout, etc). It increases domain knowledge within the team, knowledge about the codebase, and speeds up continues deployment process. One major disadvantage however, is that there is not experience out there yet. Therefor I would like to share my thoughts, experiences and choices.
Don’t choose to be technology agnostic because the internet says so
Being technology agnostic is a common advantage you will see stated when you read up on micro frontends. Be aware that this also has major disadvantages. I would say this decision should be based on the type of application that you build. In our case, we were building an ecommerce platform. This means that our application will have a lot of shared components, ( for example, a product can be displayed within any domain ). Therefor we choose not to be technology agnostic. It allowed us to create a shared web components library that is useable by anyone. Nowadays native web components are gaining more traction, so this argument could be invalid very soon in the future.
Another advantage we had not being technology agnostic, is that it allowed us to create an “app shell”. The app shell is a small library that every team uses to bootstrap their application. It includes the header, footer, authentication, server side rendering and some other features. If one of these features has a change, every team simply needs to update their NPM module to implement the changes.
Being technology agnostic can definitely work if your domains don’t need to share a lot of UI experience or state. If they do, I would recommending sharing more code and not being technology agnostic. Otherwise developing a consistent UI experience can become very challenging, or your maintenance costs ( every team implementing the same changes ) could increase dramatically when your application grows in size.
Use a BFF (backend for frontend)
If you are not familiar with the backend for frontend concept, I would suggest reading up here.
Backend for frontends are an essential concept in a micro fronted environment. It allows you to stitch microservices together and create custom API’s just for your application, handle authentication and much more.
There are several approaches for BFF’s. You can have one BFF for all your micro frontends, which is the most common approach. We choose to have a BFF per micro frontend. This allowed us to provide more flexibility to the team. For example, the account domain team, has their own account BFF. They will never have to worry about breaking changes when changing the API design of an account related feature, because they are the only consumer of their BFF / API.
Once you have different micro frontends, you need a way to stitch them together. A lot of resources online talk about a stitching application. This is an umbrella application that check the current route and fetches the corresponding micro frontend.
In our case we didn’t want a stitching application, it’s unnecessary overhead, and you are never 100% sure that the stitching server works according to design in combination with your micro frontend. In addition, we wanted more freedom for our micro frontends, so we choose that the micro frontends should be responsible for the rendering of an incoming request without having a stitching layer.
Kubernetes to the rescue
Kubernetes is an open-source container orchestration system for automating application deployment, scaling, and management. On top of that it uses ingress rules for routing. This is all we needed for the orchestration of our micro frontends. Do you want to redirect the user to a different page within your micro frontend? Use an internal push. Do you want to redirect the user to a different microfrontend? Simply use a href and kubernetes will take care of the routing. In addition, kubernetes backs up our DevOps way of working and makes the teams end 2 end responsible for their application.
Logging is going to be very important
You are now running a micro frontend architecture on production. There is an issue where users are not always able to access the correct data from a specific micro server. Good luck debugging! Debugging is gonna be hard using micro frontends, often its not entirely clear what micro frontend (or services) can cause unwanted behaviour, it could even be a combination of different micro frontends. Be sure to implement logging correctly. You will thank yourself later when random issues start to pop up. Always log the correct error codes from microservers, add a clear message what problem is occurring and be sure to use a correlation ID to track a single request. Tools like Kibana are a must.
Share knowledge between teams
Every team is responsible for their own solution, so there is not often a reason to ask another team for how to implement something. This is dangerous! Be sure to open your eyes and look around. Often when developing something, another team already faced this issue. In addition to that, it’s good to be aware of the features that other teams are working on. It’s all about what the user experiences, and that’s more than just your domain. Review code from other teams. Sit together once a week / every two weeks with all developers. Share the cool things that you and your team build!
Deploy to production as often as you can
Most importantly, enjoy and take advantage of working with micro frontends :)! You can develop and deploy features to production completely independent from other teams. In addition, your team is responsible for every feature within your domain. Develop small features and deploy often, and don’t forget to monitor the impact of the features that you create.