Lazy-Load Your Angular Components Whenever You Want

Erik Slack
ngconf
Published in
5 min readJul 7, 2021

Angular 10 included an exciting feature: the ability to lazy-load components at will. This enables us to develop applications where any components that don’t need to be loaded before showing the user the screen can be loaded when they are needing to be displayed. In the past, you would load all of your dialog components, slide-out-panels, and any other component which might not be shown until some user interaction — plus each of their dependencies — with the module that contained the route you were on. After reading this article, you’ll be able to lazy-load components at will.

What’s the Point?

It might seem innocuous to eagerly-load — what we usually do — all of your components that don’t need to be shown until some event/user-interaction. But, have you thought about those components’ dependencies? If you don’t have to load those components when the routed module gets loaded, then you won’t need the declarations, providers, modules, or anything else needed to support those components. This also means you’ll have smaller and more isolated components to test.

So with this technique, you’ll get smaller bundle sizes and more control over what gets loaded and when it gets loaded.

How It’s Done

It’s important to understand that this technique can be used at any time to preload modules as you wish, but to teach this concept as simply as possible I’m going to focus on lazy-loading a dialog — aka modal — for inspecting a user’s details. This dialog should pop up after the user clicks on a specific user in a list or table of users. I’ve used this skill for plenty of other use-cases too, so don’t fret that I chose users and user details for this example.

Step 1: Create Your Dialog Component as Usual

For this use case, we want to display a dialog containing a detailed view of a user. The process using Angular Material dialogs only requires two steps:

  1. Create a new component for the body of the dialog.
  2. Have some code in the class of the parent component triggering the opening of the dialog.

Step 2: Add a Module to the Dialog Component

Now let’s convert this component to one that can be lazy-loaded by adding a module to it. Normally we’ll have one class per file as is the best practice, but in this case, I will display them in a single file to show all that is required to accomplish lazy-loading a component.

Something to note is that it’s not a good idea to import this component into any other module ever because then it will be eagerly-loaded in spite of your work to make it load lazily. So, I recommend never making this module class exportable so that it can’t be accidentally imported. That’s another reason why it’s sort of perfect to keep both the component and the module in the same file.

Step 3: Asynchronously Import Component then Open Dialog

The last step is to change the way we open our dialog. We can’t just open the dialog anymore, we have to wait for the UserDetailDialogComponent to be loaded before attempting to open our dialog.

First, add a class property that is set equal to your import statement for the dialog component that returns a promise containing the UserDetailDialogComponent reference.

Second, call .then on your property using the component as your parameter to the arrow function. The function body provides a loaded component that can be opened by the dialog provider.

Conclusion

It only took two short steps after creating your dialog to make it lazy-loaded. No extra npm packages required.

It’s a powerful technique that could greatly decrease your bundle sizes especially if you use it for any parts of the view that don’t need to immediately appear when the page loads. You could load entirely different versions of the view for mobile than for desktop in case the user resizes the window. You could even use this technique to preload components and modules at will.

Feel free to let me know in the comments if you have any questions, enhancements, or fixes. I appreciate you for reading this and feel free to clap if you liked this article — you can go up to 50 if this helped you a ton! I check back from time to time to feel the love and make minor improvements.

Next Steps

Angular Experience Podcast Logo, fox jumping down from A
Angular Experience Podcast is for developers and all kinds of tech persons just like you!

You might’ve seen on my twitter that I’m a Co-Producer & Co-Host of the Angular Experience Podcast. Sometimes we get so caught up in writing Angular code, that we don’t take as much time to level up the other super vital skills related to our jobs. The Angular Experience Podcast, aka NgXP, is a podcast for the Angular Community by the Angular Community and beyond. Brooke Avery and I are meeting with some of the heroes in our community to help empower you to succeed in your tech career and personal life.

Come check it out @NgXP_Show on Twitter. You can subscribe to our show on any of your favorite podcast platforms!

Now that you’ve read this article and learned a thing or two (or ten!), let’s kick things up another notch!
Take your skills to a whole new level by joining us in person for the world’s first MAJOR Angular conference in over 2 years! Not only will You be hearing from some of the industry’s foremost experts in Angular (including the Angular team themselves!), but you’ll also get access to:

  • Expert panels and Q&A sessions with the speakers
  • A friendly Hallway Track where you can network with 1,500 of your fellow Angular developers, sponsors, and speakers alike.
  • Hands-on workshops
  • Games, prizes, live entertainment, and be able to engage with them and a party you’ll never forget

We’ll see you there this August 29th-Sept 2nd, 2022. Online-only tickets are available as well.
https://2022.ng-conf.org/

--

--

Erik Slack
ngconf
Editor for

Husband | Dad | Dev | He/Him (cis) GDE in Angular | SE Technical Lead at Cisco | #BlackLivesMatter