JavascriptPersonal

Angular Module Lazy Loading like a Pro

Lemme begin by saying, I’m sorry for all the frustration you’ve had to go through before arriving here (assuming you found this article via search results.) I’ve been there before, and I hope this article clears all the confusions you came here with. Angular Module Lazy Loading, when understood, is simple.

Angular Universal Server Side Rendering is now easier. See how to deploy your SSR in production.

Except many articles assume readers know so much or the readers are so fresh the examples make no real-world sense.

In this article, we consider this scenario:

  • You have an Angular 5 project.
  • Which comes with the default, AppModule (src/app/app.module.ts)
  • In addition, you’ve created two modules
    • The AuthModule(src/app/auth/auth.module.ts) which is responsible for all your authentication needs i.e login, register, forgot password, etc.
    • And the AccountModule(src/app/account/account.module.ts) which is responsible for all user account related stuff i.e change password, update user profile, etc. This module requires authentication to access.

Now, let’s say we want to lazy load the AuthModule and AccountModule. How would we go about it?

Let’s do it then.

Our AppModule & app.routing.ts

Shall we cut to the meat (code) right away?

Here’s our typicalapp.module.ts file.

import { BrowserModule } from '@angular/platform-browser';
import { NgModule } from '@angular/core';
import { AppComponent } from './app.component';
import { AppRouting } from './app.routing'; // <----------- Take note of this.
import { HttpModule } from '@angular/http';
import { FormsModule } from '@angular/forms';

// Providers
// Any providers you might have here

// Pipes
// Any pipes you might have

@NgModule({
  declarations: [
    AppComponent,
  ],
  imports: [
    BrowserModule,
    HttpModule,
    FormsModule,
    AppRouting,
  ],
  exports: [],
  providers: [],
  bootstrap: [AppComponent]
})
export class AppModule { }

And then our typical app.routing.ts will be like this:

import { ModuleWithProviders } from '@angular/core';
import { Routes, RouterModule } from '@angular/router';

const appRoutes: Routes = [
  { path: 'auth', loadChildren: './auth/auth.module#AuthModule' },
  { path: 'account', loadChildren: './account/account.module#AccountModule'},
];

export const AppRouting: ModuleWithProviders = RouterModule.forRoot(appRoutes);

Honestly, we’re done. You can move on with your life.

That’s all it takes to do lazy loading in Angular. You use the loadChildren option and point to the module file (without the extension name, namely .ts) and reference the exported name in the module file, namely, the AuthModule after a #

Done.

When you ng serve or ng build --prod you should see the modules as chunks. Like this:

Modules Lazy Loading Chunks
Modules Lazy Loading Chunks

The highlighted lines are the are the chunks created automatically by Angular. These chunks WILL be loaded ONLY when any component from that module is referenced. It happens automatically.

AuthModule‘s routing as example

When you’re using the Lazy Loading approach, the loaded module’s route should have '' path in there to have it loaded.

For example, using the auth-module.routing.ts:

import { NgModule } from '@angular/core';
import { Routes, RouterModule } from '@angular/router';
import { LoginRegisterComponent } from './login-register/login-register.component';
import { ResetPasswordComponenet } from './reset-password/reset-password.component';

const routes: Routes = [
    { path: '', component: LoginRegisterComponent }, // <-------- Without this, 
                                                     // the module will load with a blank screen
                                                     // as there's no route to handle the request.
    { path: 'reset-password/:token', component: ResetPasswordComponenet },
  ];

@NgModule({
  imports: [RouterModule.forChild(routes)],
  exports: [RouterModule],
  providers: []
})
export class AuthRoutingModule { }

You might go in to throw in any Authentication guard you want. For example, using account-module.routing.ts as example:

import { NgModule } from '@angular/core';
import { Routes, RouterModule } from '@angular/router';
import { ProfileComponent } from './profile/profile.component';
import { AuthGuard } from '../providers/auth-guard.service';

const routes: Routes = [
    { path: '', component: NavsComponent, canActivate: [AuthGuard] },
    { path: 'profile', component: InterestComponent, canActivate: [AuthGuard]},
  ];

@NgModule({
  imports: [RouterModule.forChild(routes)],
  exports: [RouterModule],
  providers: []
})
export class AccountRoutingModule { }

Conclusion

I think the above provides a typical setup of an application and how the lazy loading is implemented. Lemme know of any questions you might have below in the comments.

See you in the next one.

 

Related Articles

Back to top button