Rajendra Taradale
How to Lazy load modules dynamically in angular project
By Rajendra Taradale in Angular on Mar 14 2019
  • Pranam Bhat
    May, 2021 21

    1)Component with no module:If we want to lazy-load a component dynamically (with no module), then we can use the same pattern as with routes :// @ViewChild('myContainer', { read: ViewContainerRef }) container: ViewContainerRef;const { MyLazyComponent } = await import('./path/to/lazy/component'); const componentFactory = this.componentFactoryResolver.resolveComponentFactory(MyLazyComponent); const { instance } = this.container.createComponent(componentFactory);2)Modules:If the component depends on other services / components then we need to load the full module. Because it will be lazy loaded (not compiled initially) we need to run the compilation "manually". It is still easier than previous tricks used on previous versions of Angular. Here is a solution.We can create a service that store module references, and load the component into a container (given a module ID and a container reference).import { Injectable, Compiler, Injector } from '@angular/core';@Injectable({providedIn: 'root' }) export class LazyComponentService {private componenttRefs = {myFirstLazyModuleId: import('../path/to/first/lazy/module/component.module'),mySecondLazyModuleId: import('../path/to/second/lazy/module/component.module')};constructor(private compiler: Compiler,private injector: Injector,) { }async loadComponent(moduleId, container) {let ref;try {const moduleObj = await this.componenttRefs[moduleId];const module = moduleObj[Object.keys(moduleObj)[0]];const moduleFactory = await this.compiler.compileModuleAsync(module);const moduleRef: any = moduleFactory.create(this.injector);const componentFactory = moduleRef.instance.resolveComponent();ref = container.createComponent(componentFactory, null, moduleRef.injector);} catch (e) {console.error(e);}return ref;}} Modules need to be compiled. We do it by calling resolveComponentFactory inside each module's constructor :@NgModule({imports: [MyModules...],declarations: [MyFirstLazyComponent] }) export class MyFirstLazyComponentModule {constructor(private componentFactoryResolver: ComponentFactoryResolver) { }public resolveComponent(): ComponentFactory {return this.componentFactoryResolver.resolveComponentFactory(MyFirstLazyComponent);}} And then the magic is up, you can dynamically lazy load a component to a container :const myFirstLazyComponent = await this.lazyComponentService.loadComponent(myFirstLazyModuleId, containerRef);

    • 0

Most Popular Job Functions