Micro Frontend Architectures: what are your options?

Micro-frontends are becoming increasingly popular as a way to break down monolithic frontends into manageable, independently deployable modules. This enables different teams to work on various parts of a larger application, speeding up development and improving maintainability.
However, with multiple ways to implement micro-frontends — it’s important to select the right approach for your project.
Here we’ll explore a few common strategies for implementing micro-frontends, their pros and cons, and introduce some lesser-known but viable alternatives.
TLDR;
When building micro-frontends, choosing the right architecture is crucial.
- Federated Modules offer a solid, widely supported approach with dynamic module sharing.
- Import Maps and Native Federation provide lightweight alternatives that reduce tooling overhead
- Single-SPA and Web Components may be useful when you need to integrate multiple frameworks.
- Piral and FrintJS are options for modular, extensible setups with less complexity.
#1 Federated Modules (Webpack, Vite)
Federated Modules allow dynamic module sharing between micro-frontends at runtime, reducing duplication and improving performance. This approach, popularised by Webpack’s Module Federation, is a solid choice for teams wanting to maintain independent deployments while still sharing common libraries between apps.
Pros:
- Dynamic module sharing: Reduces redundancy by sharing libraries across different parts of the app.
- Independent deployment: Teams can develop and release their own micro-frontends independently.
- Good support: Strong community backing, especially with Webpack.
Cons:
- Complex setup: Webpack configuration can become complicated, especially as the number of micro-frontends increases.
- Version conflicts: Shared dependencies, if not properly handled, can lead to version conflicts.
#2 Import Maps (Native Browser Feature)
Import Maps leverage native browser functionality to map module imports, reducing the need for complex build tooling. They allow you to control which versions of a micro-frontend or shared libraries are loaded dynamically, making them a lightweight option for orchestrating micro-frontends.
Pros:
- No bundlers required: Uses native browser features, reducing the need for extra tools.
- Independent versioning: Easily control which version of a micro-frontend is loaded at runtime.
- Simple setup: Avoid the complexity of build systems like Webpack.
Cons:
- Browser support limitations: Older browsers may require polyfills to support Import Maps.
- Lack of optimisation: Without bundlers, you miss out on features like code splitting or tree-shaking.
- Manual orchestration: Managing multiple Import Maps for large-scale projects can become tricky.
#3 Native Federation Packages
“Native Federation” packages offer a modern approach by combining browser-native functionality (like Import Maps) with dynamic dependency sharing and runtime resolution. This allows for lightweight setups while still handling more complex requirements like version control of shared dependencies.
Pros:
- Minimal tooling: Relies on native browser features, reducing overhead.
- Dynamic resolution: Dependencies and versions can be managed dynamically at runtime.
- Extensible: Similar benefits to Webpack’s Module Federation but with less complexity.
Cons:
- Newer technology: The ecosystem and community around these packages are still developing, so they may not be as mature as Webpack’s Federation.
- Fewer advanced features: Lacks some of the more sophisticated features of Webpack, such as advanced caching strategies or optimisation techniques.
#4 Single-SPA
Single-SPA is one of the more established frameworks for micro-frontends and allows multiple JavaScript frameworks (e.g., React, Angular, Vue) to coexist within a single application. It’s ideal if you’re dealing with a polyglot environment where different teams are working in different frameworks.
Pros:
- Framework-agnostic: Integrates different frameworks under one roof.
- Customisable: Offers lifecycle hooks to manage the mounting and unmounting of micro-frontends.
- Established: Backed by a large community and good documentation.
Cons:
- Complexity: Managing multiple frameworks can add complexity to the application.
- Learning curve: Requires a bit of time to get familiar with the framework’s lifecycle and orchestration methods.
#5 Piral
A lesser-known option, designed to help build modular, independently deployable micro-frontends, with strong support for modern frameworks and extensibility through plugins.
Pros:
- Modular architecture: Ideal for independent module development.
- Extensible: Built-in plugin system allows for high customisation.
- Framework support: Works well out of the box with modern frameworks.
Cons:
- Smaller ecosystem: Not as widely adopted, which may limit community support and resources.
- Initial setup: There’s some complexity involved in setting up its modular architecture.
#6 Web Components
Web Components are a standards-based way to build reusable, encapsulated components that work across different frameworks. This makes them a flexible option for micro-frontends, especially in a polyglot environment.
Pros:
- Framework-agnostic: Works with any frontend framework.
- Native browser support: No need for additional libraries or frameworks.
- Encapsulation: Strong isolation of styles and behaviour between micro-frontends.
Cons:
- Complex integration: Web Components don’t always integrate seamlessly with popular frameworks.
- Lack of tooling: Web Components don’t benefit from the same tooling that solutions like Webpack’s Module Federation offer.
- Learning curve: For teams unfamiliar with Web Components, there’s a bit of a learning curve to implement them effectively.
#7 FrintJS
FrintJS is a lightweight micro-frontend framework that provides built-in dependency injection and works well for modular development.
Pros:
- Lightweight: Minimal overhead compared to other solutions.
- Dependency injection: Built-in support for sharing services and state between micro-frontends.
- Framework support: Has first-class support for modern frameworks.
Cons:
- Smaller community: FrintJS is less commonly used, which may limit available resources and support.
- Unique architecture: Its dependency injection pattern may require a learning curve for teams used to traditional frontend frameworks.
Summary
🥇 Federated Modules (Webpack or Vite) are a solid choice if you need dynamic module sharing and independent deployment at scale. For simpler setups, Import Maps or Native Federation offer lightweight alternatives with reduced tooling overhead.
If your project involves multiple frameworks, Single-SPA or Web Components may be the better fit, but they come with added complexity and learning curves. For teams focused on modularity and extensibility, Piral or FrintJS can be worth exploring.
By understanding the pros and cons of each approach, you can make an informed decision that best fits your team and project needs.
Links
Federated Modules
- https://dev.to/abhi0498/react-micro-frontends-using-vite-30ah
- https://vercel.com/templates/next.js/microfrontends
- https://github.com/vercel/examples/tree/main/solutions/microfrontends
Import Maps
- https://javascript.plainenglish.io/its-time-to-talk-about-import-map-micro-frontend-and-nx-monorepo-0b8e2c07568a
- https://www.mercedes-benz.io/blog/2023-01-05-you-might-not-need-module-federation-orchestrate-your-microfrontends-at-runtime-with-import-maps
Native Federation
- https://www.angulararchitects.io/en/blog/announcing-native-federation-1-0/
- https://www.npmjs.com/package/@softarc/native-federation
Single-SPA
Piral
Web Components