Lazy Load Components in Angular 12 with Ivy

At the time of its creation, Angular apps load all modules immediately irrespective of their utility and usage in the app. Enter lazy loading. To reduce the number of components the app needs to load and save on resources such as processor power and network bandwidth, we implement the lazy loading pattern in the app. Lazy loading helps keep initial bundle sizes smaller, which in turn helps decrease load times.
Lazy loading of single components has not been possible so far. However, with Angular Ivy (or just Ivy), more abilities are now possible.

Locality in Ivy

import { Component } from '@angular/core';
@Component({
selector: 'app-component',
templateUrl: './app.component.html',
styleUrls: ['./app.component.scss']
})
export class AppComponent {
title = 'my-app';
}
ng g greet - flat - skip-import

In the above command, skip-import will not import the component in the current module. We will load this component inside the module using lazy load.

import { Component, OnInit } from '@angular/core';
@Component({
selector: 'greet',
templateUrl: './greet.component.html',
styleUrls: ['./greet.component.scss']
})
export class GreetComponent implements OnInit {
constructor() { }
ngOnInit() {
}
}

We see that the greet component is created and we will pass data to this component,

@Input() message: string;
@Output() sendEventEmmiter = new EventEmitter()

For now, this is sufficient for the greet component. We will now lazy load the greet component in the app.component. To do this, we have to inject

viewContainerRef and ComponentFactoryResolver
constructor(private vcrf: ViewContainerRef, private cfr: ComponentFactoryResolver) { }

What is viewContainerRef? — This is a container in which one or more views can be attached
What is ComponentFactoryResolver? — This is a simple registry that maps Components to generated ComponentFactory classes.
These classes can be used to create instances of components. Use these to obtain the factory for a given component type, then use the factory’s create() method to create a component of that type.

Create the method

loadComponent() {
this.vcrf.clear();
import('./greet/greet.component').then(({ GreetComponent }) => {
let greetComp = this.vcrf.createComponent(
this.cfr.resolveComponentFactory(GreetComponent)
);
});
}

Here we are using promises of JavaScript. These allow us to load the component only if the promise returns successfully. We are also using viewContaierRef, and it’s method createComponent() in which we are passing componentFactoryResolver. These should be able to create the component and host inside that particular viewContainerRef.
If you see, we still are not passing any value to the greetComponent. In the above code, you will notice that we have a variable called greetComp. This variable contains a reference to a lazy loaded component that we can use to pass data.

greetComp.instance.message = 'I am from app.component';
greetComp.instance.sendEventEmmiter.subscribe(data => {
console.log(data);
});

When we combine all the above code so then our loadComponent() method will look like this,

loadComponent() {
this.greetViewchildRef.clear();
import('./greet/greet.component').then(({ GreetComponent }) => {
let greetComp = this.greetViewchildRef.createComponent(
this.cfr.resolveComponentFactory(GreetComponent)
);
greetComp.instance.message = 'I am from app.component';
greetComp.instance.sendEventEmmiter.subscribe(data => {
console.log(data);
});
});
}

Displaying the result

<div>
<ng-template #greetComp>
</ng-template>
</div>
<button (click)="loadComponent()">Load component</button>

Here we use the ng-template to load the greetComponent. We also need to add viewChild() to show the component data.

@ViewChild('greetComp', {read: ViewContainerRef}) private greetViewchildRef: ViewContainerRef

Note that if we want to use any module, then we need to add the decorator to the component itself, and then import the module within it.

@NgModule({
declarations: [GreetComponent],
imports: [FormsModule]
})
class GreetComponentModule {}

Conclusion

Developer and technical author. Read more articles at Techiediaries

Developer and technical author. Read more articles at Techiediaries