Hi, I am Trishul
🤖
👨💻
Destructuring Frontend monoliths with MicroFrontends
@trishulgoel
Monoliths
Monolithic application is designed to be self-contained; components of the program are interconnected and interdependent
Frontend Monolith
All the code in a single place
Increased inter-team dependency
Slow development to deploy cycle
Increasing size of repo everyday
Only as strong as weakest link
MICROFRONTENDS
Microfrontend architecture is a design pattern where a monolithic Frontend app is destructured into small independent(?) apps. These micro apps are stitched together as a single page on the fly.
Standalone system
Independent Repository
Independent CI Pipelines
Independent Deployments
Parallel development cycle
ARCHITECTURE
Remote 1
HOST
Remote 2
Remote 3
HEADER
FOOTER
Home Page
Product Listing
Page
Product Details
Page
Payments
and
Checkout
Cart
MicroFrontend
Appshell / Host
Appshell
Shared business Logic
Login
Tracking
System config
Routing
COMMUNICATION
Same tech stack
Share as params
Different tech stack
Custom DOM events
Custom DOM Events
HOW?
Some Traditional Approaches
Node modules
IFrames
MODULE FEDERATION
Remote 1
Remote 2
Remote 3
HOST
shared.component.ts
import { Component, OnInit } from '@angular/core';
@Component({
selector: 'app-shared-component',
templateUrl: './sharedModule.component.html',
styleUrls: ['./sharedModule.component.css']
})
export class SharedComponent implements OnInit {
constructor() {}
ngOnInit(): void {}
}
Remote config
new ModuleFederationPlugin({
name: "remote",
filename: "remoteEntry.js",
exposes: {
'./SharedModule': './src/app/shared/sharedModule.component.ts',
},
shared: {
"@angular/core": { singleton: true, strictVersion: true },
"@angular/common": { singleton: true, strictVersion: true },
"@angular/router": { singleton: true, strictVersion: true },
}
}),
Host config
new ModuleFederationPlugin({
remotes: {
"remote": "remote@http://localhost:4300/remoteEntry.js",
},
shared: {
"@angular/core": { singleton: true, strictVersion: true },
"@angular/common": { singleton: true, strictVersion: true },
"@angular/router": { singleton: true, strictVersion: true },
}
}),
Host App
import { NgModule } from '@angular/core';
import { RouterModule, Routes } from '@angular/router';
import { SharedComponent } from 'remote/SharedModule';
const routes: Routes = [
{
path: 'remote',
component: SharedComponent,
data: { from: ' Host' }
},
];
@NgModule({
imports: [RouterModule.forRoot(routes)],
exports: [RouterModule]
})
export class AppRoutingModule { }
DEMO TIME
CHALLENGES
DESIGN CONSISTENCY
Initializing new MicroFrontend
Templating engine
Tenpureto
Moving components to design system
Sharing logic between Micro Frontends
Building an efficient developer experience
Decoupling code from Appshell
THANK YOU
@trishulgoel
REFERENCES
-
https://webpack.js.org/concepts/module-federation/
-
https://github.com/module-federation/module-federation-examples
MicroFrontends | AngularDay
By Trishul Goel
MicroFrontends | AngularDay
Destructuring Frontend Monoliths with MicroFrontends
- 746