DEV Community

Krishna Bhamare
Krishna Bhamare

Posted on • Updated on

Pre-load Angular Modules🥳

Preloading

1. In preloading, feature modules are loaded in background asynchronously. In preloading, modules start loading just after application starts.
2. When we hit the application, first AppModule and modules imported by it, will be loaded eagerly. Just after that modules configured for preloading is loaded asynchronously.
3. Preloading is useful to load those features which are in high probability to be visited by user just after loading the application.
4. To configure preloading, angular provides preloadingStrategy property which is used with RouterModule.forRoot in routing module. Find the code snippet.

@NgModule({
  imports: [ 
      RouterModule.forRoot(routes,
      {
        preloadingStrategy: PreloadAllModules
      }) 
  ],
  ------
})
export class AppRoutingModule { }
Enter fullscreen mode Exit fullscreen mode

5. To configure preloading features modules, first we will configure them for lazy loading and then using Angular in-built PreloadAllModules strategy, we enable to load all lazy loading into preloading modules.
6. Using PreloadAllModules strategy, all modules configured by loadChildren property will be preloaded. The modules configured by loadChildren property will be either lazily loaded or preloaded but not both. To preload only selective modules, we need to use custom preloading strategy.
7. Once we configure PreloadAllModules strategy, then after eager loading modules, Angular searches for modules applicable for preloading. The modules configured by loadChildren will be applicable for preloading. We will take care that these feature modules are not imported in application module i.e. AppModule.
8. We can create custom preloading strategy. For this we need to create a service by implementing Angular PreloadingStrategy interface and override its preload method and then configure this service with preloadingStrategy property in routing module. To select a module for custom preloading we need to use data property in route configuration. data can be configured as data: { preload: true } for selective feature module preloading.

here we will use in-built preloading strategy i.e. PreloadAllModules strategy. Find the example.
Module and routing module for feature 1:
country.module.ts

import { NgModule }   from '@angular/core';
import { CommonModule }   from '@angular/common';
import { ReactiveFormsModule }    from '@angular/forms';
import { CountryComponent }  from './country.component';
import { CountryListComponent }  from './country-list/country.list.component';
import { CountryService } from './services/country.service';
import { CountryRoutingModule }  from './country-routing.module';

@NgModule({
  imports: [     
        CommonModule,
    ReactiveFormsModule,
    CountryRoutingModule
  ], 
  declarations: [
    CountryComponent,
    CountryListComponent
  ],
  providers: [ CountryService ]
})
export class CountryModule {
  constructor() {
    console.log('CountryModule loaded.');
  }
} 
Enter fullscreen mode Exit fullscreen mode

country-routing.module.ts

import { NgModule } from '@angular/core';
import { RouterModule, Routes } from '@angular/router';
import { CountryComponent }  from './country.component';
import { CountryListComponent }  from './country-list/country.list.component';

const countryRoutes: Routes = [
    { 
      path: '',
          component: CountryComponent,
          children: [ 
        {
          path: 'country-list',
          component: CountryListComponent
        }  
      ]
    }   
];

@NgModule({
  imports: [ RouterModule.forChild(countryRoutes) ],
  exports: [ RouterModule ]
})
export class CountryRoutingModule { }
Enter fullscreen mode Exit fullscreen mode

Module and routing module for feature 2:
person.module.ts

import { NgModule }   from '@angular/core';
import { CommonModule }   from '@angular/common';
import { ReactiveFormsModule }    from '@angular/forms';
import { PersonComponent }  from './person.component';
import { PersonListComponent }  from './person-list/person.list.component';
import { PersonService } from './services/person.service';
import { PersonRoutingModule }  from './person-routing.module';

@NgModule({
  imports: [     
    CommonModule,
    ReactiveFormsModule,
    PersonRoutingModule
  ], 
  declarations: [
    PersonComponent,
    PersonListComponent
  ],
  providers: [ PersonService ]
})
export class PersonModule { 
  constructor() {
    console.log('PersonModule loaded.');
  }
}
Enter fullscreen mode Exit fullscreen mode

person-routing.module.ts

import { NgModule } from '@angular/core';
import { RouterModule, Routes } from '@angular/router';
import { PersonComponent }  from './person.component';
import { PersonListComponent }  from './person-list/person.list.component';

const personRoutes: Routes = [
    { 
      path: '',
          component: PersonComponent,
      children: [ 
        {
          path: 'person-list',
          component: PersonListComponent
        }
      ]
    }  
];

@NgModule({
  imports: [ RouterModule.forChild(personRoutes) ],
  exports: [ RouterModule ]
})
export class PersonRoutingModule { }
Enter fullscreen mode Exit fullscreen mode

Now find the AppModule and AppRoutingModule.
app.module.ts

import { NgModule }   from '@angular/core';
import { BrowserModule } from '@angular/platform-browser';
import { AppComponent }  from './app.component';
import { AddressComponent }  from './address.component';
import { PageNotFoundComponent }  from './page-not-found.component';
import { AppRoutingModule }  from './app-routing.module';

@NgModule({
  imports: [     
    BrowserModule,
    AppRoutingModule
  ],
  declarations: [
    AppComponent,
    AddressComponent,
    PageNotFoundComponent
  ],
  providers: [ ],
  bootstrap: [ AppComponent ]
})
export class AppModule { 
  constructor() {
     console.log('AppModule loaded.');
  }
}
Enter fullscreen mode Exit fullscreen mode

app-routing.module.ts

import { NgModule } from '@angular/core';
import { RouterModule, Routes } from '@angular/router';
import { PreloadAllModules } from '@angular/router';
import { AddressComponent } from './address.component';
import { PageNotFoundComponent } from './page-not-found.component';

const routes: Routes = [
   {
      path: 'country',
      loadChildren: () => import('./country/country.module').then(mod => mod.CountryModule)
   },
   {
      path: 'person',
      loadChildren: () => import('./person/person.module').then(mod => mod.PersonModule)
   },
   {
      path: 'address',
      component: AddressComponent
   },
   {
      path: '',
      redirectTo: '',
      pathMatch: 'full'
   },
   {
      path: '**',
      component: PageNotFoundComponent
   }
];

@NgModule({
   imports: [
      RouterModule.forRoot(routes,
         {
            preloadingStrategy: PreloadAllModules
         })
   ],
   exports: [
      RouterModule
   ]
})
export class AppRoutingModule { } 
Enter fullscreen mode Exit fullscreen mode

We can see in the AppRoutingModule that we are using PreloadAllModules strategy for preloading. The module configured by loadChildren i.e. CountryModule and PersonModule will be preloaded.
Output
When we hit the application for first time, we can see following logs in browser console.

AppModule loaded.
Angular is running in the development mode. Call enableProdMode() to enable the production mode.
CountryModule loaded.
PersonModule loaded.

Enter fullscreen mode Exit fullscreen mode

We can observe that application started after loading AppModule and then application preloaded CountryModule and PersonModule.

Checkout to main blog Angular Module Loading strategies

Top comments (0)