{"id":528,"date":"2020-10-27T13:35:51","date_gmt":"2020-10-27T12:35:51","guid":{"rendered":"https:\/\/nguenkam.com\/blog\/?p=528"},"modified":"2020-11-11T10:02:16","modified_gmt":"2020-11-11T09:02:16","slug":"angular-performance-analysis-with-webpack-bundle-analyzer","status":"publish","type":"post","link":"https:\/\/nguenkam.com\/blog\/index.php\/2020\/10\/27\/angular-performance-analysis-with-webpack-bundle-analyzer\/","title":{"rendered":"Angular: Performance Analysis with webpack Bundle Analyzer"},"content":{"rendered":"\n<p>Web performance is possibly one of the most important parts to take into account for a modern web application. The thing is, it\u2019s easier than ever to add third party modules and tools to our projects, but this can come with a huge performance tradeoff.<\/p>\n\n\n\n<p>This becomes even more difficult the larger a project becomes, therefore, this article looks at how to use webpack Bundle Analyzer with Angular to help visualize where code in the final bundle comes from.<\/p>\n\n\n\n<h4>New project and Adding Dependencies<\/h4>\n\n\n\n<p>To establish a common base, we\u2019ll create a brand new Angular application and add some dependencies:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code># Install the Angular CLI globally\n$ npm i @angular\/cli -g\n\n# Create a new Angular project of your choosen name &amp;&amp; change directory\n$ ng new AngularBundleAnalyser\n\n> N\n> SCSS\n\n$ cd AngularBundleAnalyser\n\n$ npm i moment\n$ npm i firebase\n\n# Open this up in VS Code\n$ code . &amp;&amp; ng serve<\/code><\/pre>\n\n\n\n<p>We can then head over to&nbsp;<code>app.component.ts<\/code>&nbsp;and import these into our&nbsp;<code>main.js<\/code>&nbsp;bundle:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>import { Component, OnInit } from '@angular\/core';\nimport * as moment from 'moment';\nimport * as firebase * from 'firebase';\n\n@Component({\n  selector: 'app-root',\n  templateUrl: '.\/app.component.html',\n  styleUrls: &#91;'.\/app.component.scss']\n})\nexport class AppComponent  implements OnInit {\n  ngOnInit(): void {\n    const time = moment.utc();\n    const firebaseConfig = {};\n    firebase.initializeApp(firebaseConfig);\n  }\n}<\/code><\/pre>\n\n\n\n<p><span class=\"has-inline-color has-vivid-red-color\">Our bundle has gone from about 9kB to 24kB.<\/span> We should analyze this to see what we can do to get this lower. Let\u2019s install the&nbsp;<code>webpack-bundle-analyzer<\/code>&nbsp;plugin:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>$ npm i webpack-bundle-analyzer -D<\/code><\/pre>\n\n\n\n<h4>Building with stats.json<\/h4>\n\n\n\n<p>The Angular CLI gives us the ability to build with a&nbsp;<code>stats.json<\/code>&nbsp;out of the box. This allows us to pass this to our bundle analyzer and start the process.<\/p>\n\n\n\n<p>We can add a new script to&nbsp;<code>package.json<\/code>&nbsp;to add this functionality:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>\"scripts\": {\n  \"build:stats\": \"ng build --stats-json\"\n}<\/code><\/pre>\n\n\n\n<p>Now we can run&nbsp;<code>npm run build:stats<\/code>&nbsp;to generate a&nbsp;<code>stats.json<\/code>&nbsp;file inside of the&nbsp;<code>dist<\/code>&nbsp;folder! Let\u2019s do that:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>$ npm run build:stats<\/code><\/pre>\n\n\n\n<h4>Bundle Analysis<\/h4>\n\n\n\n<p>We can make another&nbsp;<code>script<\/code>&nbsp;which runs the&nbsp;<code>webpack-bundle-analyzer<\/code>&nbsp;with the&nbsp;<code>stats.json<\/code>:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>\"scripts\": {\n  \"analyze\": \"webpack-bundle-analyzer dist\/AngularBundleAnalyser\/stats.json\"\n}<\/code><\/pre>\n\n\n\n<p>Run the analyzer with the following command:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>$ npm run analyze<\/code><\/pre>\n\n\n\n<p>You should then be able to see your analysis over at&nbsp;<code>localhost:8888<\/code>:<\/p>\n\n\n\n<p>Webpack Bundle Analyzer is started at http:\/\/127.0.0.1:8888<br>Use Ctrl+C to close it<\/p>\n\n\n\n<figure class=\"wp-block-image is-resized\"><img loading=\"lazy\" src=\"https:\/\/assets.digitalocean.com\/articles\/alligator\/angular\/angular-webpack-bundle-analyzer\/webpack-bundle-analysis.png\" alt=\"webpack Bundle Analyzer\" width=\"567\" height=\"453\"\/><\/figure>\n\n\n\n<p>This tells us that we should do a better job of removing un-used items within our bundle. <span class=\"has-inline-color has-vivid-red-color\">Let\u2019s see this example by only importing&nbsp;<code>initializeApp<\/code>&nbsp;from&nbsp;<code>firebase<\/code>:<\/span><\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>import { Component, OnInit } from '@angular\/core';\nimport * as moment from 'moment'\nimport { initializeApp } from 'firebase\/app'\n  \/\/** code changed\n\n@Component({\n  selector: 'app-root',\n  templateUrl: '.\/app.component.html',\n  styleUrls: &#91;'.\/app.component.scss']\n})\nexport class AppComponent  implements OnInit {\n  ngOnInit(): void {\n    const time = moment.utc();\n    const firebaseConfig = {};\n    initializeApp(firebaseConfig);\n  }\n}<\/code><\/pre>\n\n\n\n<p>This makes the following difference within our bundle analysis:<\/p>\n\n\n\n<figure class=\"wp-block-image is-resized\"><img loading=\"lazy\" src=\"https:\/\/assets.digitalocean.com\/articles\/alligator\/angular\/angular-webpack-bundle-analyzer\/webpack-bundle-analysis-2.png\" alt=\"webpack Bundle Analysis: 2\" width=\"573\" height=\"458\"\/><\/figure>\n\n\n\n<h4>Summary<\/h4>\n\n\n\n<p>Become one with your bundle. Understand what you can do to make it smaller and further-optimized. The&nbsp;<code>webpack-bundle-analyzer<\/code>&nbsp;tool is perfect for this!<\/p>\n\n\n\n<p><\/p>\n\n\n\n<h5>Reference:<\/h5>\n\n\n\n<p><a href=\"https:\/\/www.digitalocean.com\/\">https:\/\/www.digitalocean.com\/<\/a><\/p>\n","protected":false},"excerpt":{"rendered":"<p>Web performance is possibly one of the most important parts to take into account for a modern web application. The thing is, it\u2019s easier than ever to add third party modules and tools to our projects, but this can come with a huge performance tradeoff. This becomes even more difficult the larger a project becomes, [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":680,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":[],"categories":[37],"tags":[126,127,128,107],"_links":{"self":[{"href":"https:\/\/nguenkam.com\/blog\/index.php\/wp-json\/wp\/v2\/posts\/528"}],"collection":[{"href":"https:\/\/nguenkam.com\/blog\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/nguenkam.com\/blog\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/nguenkam.com\/blog\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/nguenkam.com\/blog\/index.php\/wp-json\/wp\/v2\/comments?post=528"}],"version-history":[{"count":3,"href":"https:\/\/nguenkam.com\/blog\/index.php\/wp-json\/wp\/v2\/posts\/528\/revisions"}],"predecessor-version":[{"id":682,"href":"https:\/\/nguenkam.com\/blog\/index.php\/wp-json\/wp\/v2\/posts\/528\/revisions\/682"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/nguenkam.com\/blog\/index.php\/wp-json\/wp\/v2\/media\/680"}],"wp:attachment":[{"href":"https:\/\/nguenkam.com\/blog\/index.php\/wp-json\/wp\/v2\/media?parent=528"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/nguenkam.com\/blog\/index.php\/wp-json\/wp\/v2\/categories?post=528"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/nguenkam.com\/blog\/index.php\/wp-json\/wp\/v2\/tags?post=528"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}