Is your frontend project suffering from too many cooks in the kitchen? Is deployment mind-numbingly slow? Are you becoming locked into an obsolete technology stack? You might need micro frontends and module federation.
Here at Bitovi, we strive to stay on top of new patterns and tools. Module federation is the hottest topic in the micro frontend world, but it’s still quite new. The nextjs-mf
plugin was open-sourced a few months ago, and we’re still learning what production-grade module federation looks like. We’re exploring multiple methods for solving micro frontends; this is the latest one. We’re sharing some of what we learned and things to look out for when committing to micro frontends and module federation.
What is a Micro Frontend?
The term micro frontend is nothing more than an architectural pattern. It is the idea of splitting apart a website into many smaller-sized pieces. micro frontends provide many benefits—reusability, autonomous teams, and performance—while enforcing isolation.
There are many ways to implement micro frontends. Some popular options are iframes, remote scripts, node modules, and module federation. There are also micro frontend frameworks like single-spa, OpenComponents, and Mosaic.
What is Module Federation?
Module Federation is a run-time approach to code-sharing in JavaScript projects which is available as a plugin native to webpack5. There’s also an npm package for Next.js! A federated module can either be a host (a consumer of other modules) or a remote (a federated module that is consumed by another). Each federated module can be in its own repository and deployed independently. They all can act as bidirectional hosts, meaning they can be both a host and a remote.
Do you need Micro Frontends?
Each project and team is different. Whether module federation or micro frontends are suitable for you is something you’ll have to figure out with your squad.
Let’s break down quickly why you should and shouldn’t use micro frontends for your project, and then we can cover some reasons to consider module federation.
Reasons to Consider Micro Frontends
Here are the top three reasons to consider using micro frontends:
1. You have too many developers on one project
If your frontend project has a lot of active developers and there are parts of the app that can be developed in isolation, then this would be a great case to consider micro frontends. Converting a monolithic app into micro frontends can allow for autonomous teams. With micro frontends, a team can introduce the tools and practices that help best deliver their specific goals without stepping on the toes of another team.
2. You want to have faster releases
With bite-sized micro frontends, it’s much faster to build and deploy projects than to redeploy a monolith. This can also help move your code into your development and production environments much more quickly. The faster your code reaches the test environment, the more time you have for testing!
3. You’re looking to improve performance
Simply by loading fewer resources (only loading in what you need!), you can provide the fastest end-user experience.
Complexities Introduced by Micro Frontends
Micro frontends aren’t for every team and situation. Here are some challenges introduced by micro frontends.
1. Isolation
Also stated as a benefit to micro frontends, isolation can be a double-edged sword. Although teams will become autonomous, there must be good cross-team communication so that every consumer is aware of any interface changes. It’s also a lot easier to lose sight of the big picture when developing the app if each team is only focused on their micro frontend.
2. Performance
Wait! Wasn’t performance just listed as a reason to use micro frontends? Although micro frontends can offer benefits in terms of performance, just like isolation and autonomous teams, those benefits can be a downside. If your micro frontends are made up of all sorts of different frameworks and tools, this could quickly add up as the end user navigates around the page and has to download different JavaScript libraries on each micro frontend. This can also be solved with module federation, but more on that later.
3. Cognitive Overhead
Micro frontends introduce new challenges that aren’t typically considered when developing a traditional monolith. How do we handle data communication between micro frontends? What about server-side rendering? How is the host or entry point app orchestrating the routing and pulling in all the micro frontends?
While our objective is to make using single-spa as easy as possible, we should also note that this is an advanced architecture that is different from how front-end applications are typically done. This will require changes to existing paradigms as well as understanding of underlying tools. - single-spa
4. Data Communication
When building a frontend monolith, data communication is a problem that is already solved. Within React, we can pass props and callbacks, use contexts and reducers, and introduce external libraries such as redux for more complex data requirements. However, in the context of modular micro frontends, we typically have to rely on alternate approaches. Ideally, your micro frontends should be framework agnostic, you will have to standardize a way to pass data between micro frontends.
5. Styling
Managing and optimizing styling for your app is also something you will have to consider. Will each micro frontend be responsible for its styling? If so, how is it being imported into the host? How are nested micro frontends passing styling to the top-level host? If each micro frontend uses Material UI, how do we avoid loading in that same library several times across each frontend?
If you’ve made it this far and are still considering micro frontends, great! Let's quickly talk about module federation and whether its benefits make sense for your team.
Implementing Micro Frontends with Module Federation
Many of the complexities of micro frontends can be resolved with Module Federation. However, just like micro frontends, Module Federation isn’t the right fit for every situation. Continue reading to see whether it’s right for your team.
Benefits of Implementing Micro Frontends with Module Federation
1. Run-Time Code Sharing
This is the big one. Run-time code sharing is what module federation does best. In module federation, the modules are consumed at run-time; this not only speeds up deployment drastically but also keeps all the hosts of your micro frontend in sync. Imagine you have 3 micro frontends all-consuming the federatedModuleA. If the team responsible for federatedModuleA rolls out a hotfix or a new feature, all the host micro frontends will have the latest code the next time a user navigates to your website. If build-time sharing was used, there could be a window where a user navigates across the 3 micro frontends and sees different versions of federatedModuleA.
A traditional frontend will be deployed as a single app. With module federation there will be separate deployments and the front end will be stitched together at run time.
2. Performance
Module federation helps build on micro frontend performance benefits. You can define the shared libraries across your federated modules to avoid having duplicated dependencies loaded in, module federation will then attempt to resolve them using semantic versioning. Combined with lazy-loading the end user should only be downloading the minimal amount of resources to have the page function.
Complexities Introduced by Module Federation
1. No Versioning
This seems like a silly point to make since a big selling point of module federation is that it’s run-time code sharing. However, it’s still worth mentioning that we don’t always want run-time code sharing. Maybe you’re developing a helper function or component library and would prefer versioning. Note: you can introduce versioning using module federation and creating different remoteEntry files, but by that point, you’re better off just using npm packages.
2. Cognitive Overhead
I know this was mentioned as a micro frontend complexity, but it’s still true specifically for module federation. Introducing new technology can bring up more questions you wouldn’t have to answer when building a monolithic app. How do we leverage TypeScript for compile time errors? How do we handle data communication for nested modules? Who’s responsible for routing? How do we handle server-side rendering? Is static-site generation possible?
3. Cutting-Edge
Module federation is a new technology, it was released as a core plugin in webpack5; the Next.js library is even newer, being released as open source late last year. As with all new tools, there is a smaller community and, therefore, less support. You may run into questions that have no answers. This is something you must take into consideration if you’re up against a deadline.
Is Module Federation right for you?
It might be! We here at Bitovi are still exploring module federation and don’t have all the answers yet. I believe it might be a useful tool for a large organization and likely overkill for smaller teams. The cognitive overhead introduced by module federation and micro frontends, generally, can slow down your team rather than speed it up. In short, try and understand what you’re getting yourself into; play around with module federation and see if it’s truly what your team needs. Try to avoid hopping on the next hot tool just because it’s new. Make sure it will solve the problems your team is running into.
If you’re looking for some alternative approaches to micro frontends, then I recommend looking into:
If you want to dive deeper into module federation, these are some handy resources I’ve relied on:
Join the Conversation
Whether you want to talk about micro frontends or just chat about tech, join our Community Discord!
Got a big project up your sleeve? Our React consultants are always up for a challenge. Schedule a free consultation to see if we’d be the right fit.
Never miss an update!
Subscribe to the blog 📬