Lazy Loading vs Preloading Modules — Which should you choose?
You want to optimize your web application for users. You want quick load time. You want to use the latest new thing.
You hear about preloading modules. Its the practice of front-loading all of the modules in an application so that interacting and routing the application itself is as fast as possible — since the views are already loaded onto the client. Sounds nifty!
And in the same breath, you hear about lazy-loading modules. Its the practice of only loading the modules you need onto the client as you need them, so the browser has a minimal initial download size and therefore has the quickest entry time. Also very cool!
But these sound like they’re competing ideologies — load all modules in the beginning, or load as few as possible only when needed?
Here’s the thing: they play extremely well together, and using both is probably the most optimal way to handle module loading in your application.
Lets break down how these two work.
When using lazy loading, you’ll have an initial small download — a fraction of the overall application size. But once you navigate to another view, you’ll have another page load… rinse and repeat for each new view.
Complementing lazy loading with preloading, the module loader waits for a period of inactivity after the initial page load to start downloading the rest of the modules. Which means downloading only occurs in the background, when the user isn’t requiring those resources.
With both working together, we get the benefits of:
- Small initial page load, so the user can start interacting as quickly as possible.
- Fast navigation and interaction, since the rest of the application is loaded to the client once the browser detects inactivity.
- Most importantly: No negative side effects for the user.
I’m sold, how do I do it?
In Angular (2+), its actually pretty simple. Here’s an example app-router.module.ts:
Angular provides PreloadAllModules natively, so we import it from the router.
Then we define our lazy-loaded routes. Notice that we haven’t imported any of these routes’ modules, but we have told the route what module we’ll be looking for once its called. This is how our lazy-loading works, and it’ll work for any route defined in this file.
Finally, in our @NgModule, we import our new preloading strategy in the forRoot.
That’s all! It takes just a few quick additions to make your application optimized for user interaction.
If you’d like to get into more advanced features of these, including custom preloading strategies and a deeper dive into lazy-loading, check out Victor Savkin’s article from October 2016.