<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Hussein AbdElaziz</title>
    <description>The latest articles on DEV Community by Hussein AbdElaziz (@hussein_abdelaziz).</description>
    <link>https://dev.to/hussein_abdelaziz</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F4016424%2Ff4c0ea2a-a7bb-4ccc-b181-2151508099df.jpeg</url>
      <title>DEV Community: Hussein AbdElaziz</title>
      <link>https://dev.to/hussein_abdelaziz</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/hussein_abdelaziz"/>
    <language>en</language>
    <item>
      <title>See every wasted re-render in your Angular app</title>
      <dc:creator>Hussein AbdElaziz</dc:creator>
      <pubDate>Mon, 06 Jul 2026 13:54:44 +0000</pubDate>
      <link>https://dev.to/hussein_abdelaziz/see-every-wasted-re-render-in-your-angular-app-3alp</link>
      <guid>https://dev.to/hussein_abdelaziz/see-every-wasted-re-render-in-your-angular-app-3alp</guid>
      <description>&lt;p&gt;Angular's change detection is powerful, and completely invisible. You can &lt;em&gt;feel&lt;/em&gt; a slow app — janky scrolls, laggy inputs — but you can't &lt;em&gt;see&lt;/em&gt; which components are re-rendering, how often, or whether any of that work was actually necessary.&lt;/p&gt;

&lt;p&gt;React developers have had &lt;a href="https://github.com/aidenybai/react-scan" rel="noopener noreferrer"&gt;&lt;code&gt;react-scan&lt;/code&gt;&lt;/a&gt; for a while: flip it on, and re-renders light up on the screen. Angular had no equivalent.&lt;/p&gt;

&lt;p&gt;So I built one.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Ffto9zunbdtwa54ixe9qn.gif" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Ffto9zunbdtwa54ixe9qn.gif" alt="angular-scan highlighting re-renders in real time" width="760" height="521"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  What angular-scan does
&lt;/h2&gt;

&lt;p&gt;&lt;a href="https://www.npmjs.com/package/angular-scan" rel="noopener noreferrer"&gt;&lt;code&gt;angular-scan&lt;/code&gt;&lt;/a&gt; hooks into Angular's dev-mode profiler and paints re-renders directly onto your running app:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Yellow flash&lt;/strong&gt; — the component was checked &lt;em&gt;and&lt;/em&gt; the DOM actually changed. A real render.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Red flash&lt;/strong&gt; — the component was checked but the DOM did &lt;strong&gt;not&lt;/strong&gt; change. A wasted render.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Counter badges&lt;/strong&gt; — a cumulative render count pinned to each component's host element.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;A floating HUD&lt;/strong&gt; — total checks, wasted renders, runtime toggles, and a per-component inspector you can drill into.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;One line in &lt;code&gt;app.config.ts&lt;/code&gt; and you're scanning. It works with both zone.js and zoneless apps, and it's tree-shaken out of production entirely when &lt;code&gt;isDevMode()&lt;/code&gt; returns &lt;code&gt;false&lt;/code&gt; — zero overhead in your shipped bundle.&lt;/p&gt;

&lt;h2&gt;
  
  
  But the library has a hard limit
&lt;/h2&gt;

&lt;p&gt;The library is great — for apps you own. Even with the imperative &lt;code&gt;scan()&lt;/code&gt; API for micro-frontends where you can't touch the providers, it still has to be &lt;em&gt;installed in the project and present in the build&lt;/em&gt;. It needs to ship with your code.&lt;/p&gt;

&lt;p&gt;But a lot of the time, that's exactly what you don't have. You want to inspect a deployed dev build you didn't write, audit a third-party Angular app, or just take a quick look at your own project without adding a dependency and restarting the dev server.&lt;/p&gt;

&lt;p&gt;The library can't reach any of those. So I built something that can.&lt;/p&gt;

&lt;h2&gt;
  
  
  The angular-scan Chrome extension
&lt;/h2&gt;

&lt;p&gt;The &lt;a href="https://chromewebstore.google.com/detail/angular-scan/bgdecfngmafoiopdckbffadnjcfmcdli" rel="noopener noreferrer"&gt;extension&lt;/a&gt; brings the same overlay to any Angular app running in dev mode — no npm install, no provider, no restart. It auto-detects Angular (the toolbar badge tells you exactly what it found: dev build, production build, or no Angular at all), it's &lt;strong&gt;off by default and enabled per site&lt;/strong&gt;, and it adds three things the library can't:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;1. Exportable reports.&lt;/strong&gt; A per-component table with renders, wasted renders, and renders-per-second (current and peak), sortable by any column — exportable as JSON or CSV, plus a full-page report viewer with summary cards and a "busiest components" chart. Drop it in a performance audit, or share a snapshot with your team.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;2. Source location resolution.&lt;/strong&gt; It reads the source location the Angular compiler embeds in dev builds, and falls back to scanning your bundles' source maps when that's stripped (looking at you, webpack/Nx setups) — so you see &lt;code&gt;AppHeaderComponent — src/app/header/header.component.ts:12&lt;/code&gt;, not just a class name. This alone turns "something's re-rendering a lot" into "&lt;em&gt;this line&lt;/em&gt; is re-rendering a lot." Clicking a row even flashes the component on the page.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;3. DOM seeding on enable.&lt;/strong&gt; The component table is populated the moment you turn it on, instead of staying empty until you happen to trigger renders.&lt;/p&gt;

&lt;h2&gt;
  
  
  Library or extension — which one?
&lt;/h2&gt;

&lt;p&gt;Both do the same core thing. The difference is &lt;em&gt;access&lt;/em&gt;:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;&lt;/th&gt;
&lt;th&gt;Library&lt;/th&gt;
&lt;th&gt;Extension&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Setup&lt;/td&gt;
&lt;td&gt;One line in &lt;code&gt;app.config.ts&lt;/code&gt; (or &lt;code&gt;scan()&lt;/code&gt; for MFEs)&lt;/td&gt;
&lt;td&gt;Install, enable on the site, done&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Present in your build&lt;/td&gt;
&lt;td&gt;Yes&lt;/td&gt;
&lt;td&gt;No&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Best for&lt;/td&gt;
&lt;td&gt;Apps you own; team-wide dev; CI/programmatic use&lt;/td&gt;
&lt;td&gt;Third-party apps, deployed dev builds, quick audits&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Reports (JSON/CSV)&lt;/td&gt;
&lt;td&gt;—&lt;/td&gt;
&lt;td&gt;Yes&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Source file:line resolution&lt;/td&gt;
&lt;td&gt;—&lt;/td&gt;
&lt;td&gt;Yes&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Rule of thumb: &lt;strong&gt;your app → library&lt;/strong&gt;, &lt;strong&gt;someone else's app → extension&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;Both require &lt;strong&gt;Angular 20 or newer&lt;/strong&gt; (tested on 20, 21, and 22) running in &lt;strong&gt;development mode&lt;/strong&gt; — production builds strip the profiler hooks by design.&lt;/p&gt;

&lt;h2&gt;
  
  
  Try it
&lt;/h2&gt;

&lt;p&gt;If it helps you catch one wasted render that was quietly tanking your frame rate, it did its job.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Live demo: &lt;a href="https://husseinabdelaziz.github.io/angular-scan" rel="noopener noreferrer"&gt;https://husseinabdelaziz.github.io/angular-scan&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;npm: &lt;a href="https://www.npmjs.com/package/angular-scan" rel="noopener noreferrer"&gt;https://www.npmjs.com/package/angular-scan&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;Chrome Web Store: &lt;a href="https://chromewebstore.google.com/detail/angular-scan/bgdecfngmafoiopdckbffadnjcfmcdli" rel="noopener noreferrer"&gt;https://chromewebstore.google.com/detail/angular-scan/bgdecfngmafoiopdckbffadnjcfmcdli&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;GitHub: &lt;a href="https://github.com/husseinAbdElaziz/angular-scan" rel="noopener noreferrer"&gt;https://github.com/husseinAbdElaziz/angular-scan&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;Deep dive — library: &lt;a href="https://hussein.ee/blog/angular-scan" rel="noopener noreferrer"&gt;https://hussein.ee/blog/angular-scan&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;Deep dive — extension: &lt;a href="https://hussein.ee/blog/angular-scan-extension" rel="noopener noreferrer"&gt;https://hussein.ee/blog/angular-scan-extension&lt;/a&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;If you give it a spin, I'd love to hear what wasted renders you find. A star ⭐ on GitHub keeps the project going.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Written by me; structure and editing polished with Claude.&lt;/em&gt;&lt;/p&gt;

</description>
      <category>angular</category>
      <category>performance</category>
      <category>webdev</category>
      <category>devtools</category>
    </item>
  </channel>
</rss>
