Angular Performance Optimization

Master Angular Performance Optimization with OnPush Change Detection, Signals, Lazy Loading, Deferrable Views, trackBy, Virtual Scrolling, SSR, Hydration, RxJS optimization, architecture diagrams, enterprise best practices, and interview questions.

Performance optimization is one of the most important aspects of enterprise Angular development.

A fast application provides:

  • Better user experience
  • Faster page loads
  • Lower memory usage
  • Reduced CPU utilization
  • Better SEO
  • Improved scalability

Modern Angular (v17+) introduces several powerful performance features including:

  • Signals
  • OnPush Change Detection
  • Deferrable Views
  • Hydration
  • Standalone Components
  • Optimized Rendering

This guide covers the most important Angular performance optimization techniques used in production applications.


Table of Contents

  • Why Performance Matters
  • Performance Architecture
  • Lazy Loading
  • Standalone Components
  • OnPush Change Detection
  • Signals
  • Computed Signals
  • trackBy
  • Virtual Scrolling
  • Deferrable Views
  • Image Optimization
  • SSR & Hydration
  • RxJS Optimization
  • Bundle Optimization
  • Enterprise Banking Example
  • Performance Checklist
  • Top 10 Interview Questions
  • Summary

Why Performance Matters

Performance directly affects:

  • User satisfaction
  • SEO rankings
  • Mobile experience
  • Server costs
  • Conversion rates

A high-performance Angular application should:

  • Load quickly
  • Render efficiently
  • Minimize network requests
  • Update only affected UI
  • Use memory efficiently

Performance Architecture

flowchart TD

User

User --> LazyLoading

LazyLoading --> Signals

Signals --> OnPush

OnPush --> ComputedSignals

ComputedSignals --> OptimizedRendering

OptimizedRendering --> DOM

1. Lazy Loading

Load feature modules only when needed.

Instead of downloading the entire application initially,

Angular loads feature code only when users navigate to it.

export const routes: Routes = [

{

path:'admin',

loadComponent: () =>

import('./admin/admin.component')

.then(m => m.AdminComponent)

}

];

Benefits

  • Smaller initial bundle
  • Faster startup
  • Better scalability

Lazy Loading Architecture

flowchart LR

Browser

Browser --> HomeBundle

Browser --> AdminRoute

AdminRoute --> AdminBundle

2. Standalone Components

Modern Angular recommends Standalone Components.

@Component({

standalone:true,

selector:'app-home',

templateUrl:'./home.html'

})

export class HomeComponent{}

Benefits

  • Smaller bundles
  • Simpler architecture
  • Better tree shaking
  • Faster compilation

3. OnPush Change Detection

Use OnPush for feature components.

@Component({

changeDetection:

ChangeDetectionStrategy.OnPush

})

Benefits

  • Fewer Change Detection cycles
  • Lower CPU usage
  • Better rendering performance

Default vs OnPush

Feature Default OnPush
Checks Every Cycle ✅ Yes ❌ No
Enterprise Ready ⚠️
Performance Good Excellent

4. Use Signals for UI State

Signals provide fine-grained rendering.

counter = signal(0);

increment(){

this.counter.update(

value => value + 1

);

}

Only dependent views update.


Signals Rendering

flowchart LR

Signal

Signal --> Component

Component --> UpdatedDOM

5. Use Computed Signals

Avoid duplicated calculations.

❌ Wrong

total = signal(0);

updateTotal(){

this.total.set(

this.price()

+

this.tax()

);

}

✅ Correct

total = computed(() =>

this.price()

+

this.tax()

);

Benefits

  • Automatic recalculation
  • Memoization
  • Less code

6. Use trackBy with Lists

Without trackBy, Angular may recreate every DOM element.

<li *ngFor="let user of users">

{{user.name}}

</li>

<li

*ngFor="let user of users;

trackBy:trackById">

{{user.name}}

</li>
trackById(

index:number,

user:User

){

return user.id;

}

Benefits

  • Fewer DOM updates
  • Better scrolling
  • Faster rendering

trackBy Architecture

flowchart LR

OldList

OldList --> TrackBy

TrackBy --> ReusedDOM

ReusedDOM --> UpdatedList

7. Virtual Scrolling

Render only visible items.

Instead of rendering 100,000 rows,

Angular renders only visible rows.

<cdk-virtual-scroll-viewport

itemSize="60">

<div

*cdkVirtualFor="let user of users">

{{user.name}}

</div>

</cdk-virtual-scroll-viewport>

Benefits

  • Lower memory usage
  • Smooth scrolling
  • Faster rendering

Virtual Scrolling

flowchart TD

LargeDataset

LargeDataset --> VisibleItems

VisibleItems --> DOM

8. Deferrable Views

Modern Angular supports deferred loading.

@defer {

<app-recommendations/>

}

@placeholder {

Loading...

}

Benefits

  • Faster first paint
  • Smaller initial rendering cost
  • Improved Core Web Vitals

Deferrable View Flow

flowchart LR

PageLoad

PageLoad --> MainContent

MainContent --> DeferredContent

9. Image Optimization

Best practices

  • Use modern formats (WebP, AVIF)
  • Compress large images
  • Lazy-load offscreen images
  • Specify width and height
  • Serve responsive images
<img

src="hero.webp"

loading="lazy"

width="600"

height="400"

alt="Dashboard">

Benefits

  • Faster loading
  • Reduced bandwidth
  • Better Largest Contentful Paint (LCP)

10. SSR and Hydration

Server-Side Rendering generates HTML on the server.

Hydration attaches Angular behavior without recreating the DOM.

flowchart LR

Server

Server --> HTML

HTML --> Browser

Browser --> Hydration

Hydration --> InteractiveUI

Benefits

  • Better SEO
  • Faster First Contentful Paint (FCP)
  • Better Largest Contentful Paint (LCP)

11. Optimize RxJS

Avoid unnecessary subscriptions.

Use the Async Pipe.

<div>

{{ users$ | async | json }}

</div>

Use operators wisely.

search$

.pipe(

debounceTime(300),

distinctUntilChanged(),

switchMap(

term =>

this.search(term)

)

);

Benefits

  • Reduced API calls
  • Better responsiveness
  • Automatic subscription cleanup

12. Bundle Optimization

Recommendations

  • Remove unused libraries
  • Use tree shaking
  • Lazy-load large features
  • Avoid duplicate dependencies
  • Enable production builds
ng build --configuration production

Benefits

  • Smaller JavaScript bundles
  • Faster downloads
  • Improved startup time

Enterprise Banking Example

Banking Dashboard

Optimization Techniques

  • Standalone Components
  • Lazy Loading
  • Signals
  • Computed Signals
  • OnPush
  • Virtual Scrolling
  • SSR
  • Hydration
  • Deferrable Views
  • RxJS Optimization

Architecture

flowchart TD

Browser

Browser --> SSR

SSR --> Hydration

Hydration --> Signals

Signals --> OnPush

OnPush --> Dashboard

Dashboard --> VirtualScroll

Dashboard --> DeferredWidgets

Dashboard --> OptimizedUI

Benefits

  • Faster startup
  • Lower memory usage
  • Reduced CPU utilization
  • Excellent scalability
  • Better user experience

Performance Optimization Checklist

Optimization Benefit
Lazy Loading Smaller initial bundle
Standalone Components Better tree shaking
OnPush Fewer checks
Signals Fine-grained rendering
Computed Signals Memoization
trackBy Less DOM recreation
Virtual Scrolling Lower memory usage
Deferrable Views Faster initial render
SSR Better SEO
Hydration Faster interactivity
Async Pipe Automatic subscriptions
Production Build Smaller bundle

Common Performance Mistakes

Mutating Objects

❌ Wrong

this.user.name = 'John';

✅ Correct

this.user = {

...this.user,

name:'John'

};

Missing trackBy

Large lists without trackBy cause unnecessary DOM recreation.


Manual Subscriptions Everywhere

Prefer the Async Pipe whenever rendering Observable data.


Heavy Template Methods

{{ calculateTotal() }}

total = computed(() =>

this.calculateTotal()

);

Loading Everything Initially

Lazy-load large features and defer non-critical UI.


Performance Best Practices

  • Use Standalone Components.
  • Lazy-load feature areas.
  • Prefer OnPush for feature components.
  • Use Signals for local UI state.
  • Use Computed Signals for derived values.
  • Use immutable updates.
  • Add trackBy to large lists.
  • Use Virtual Scrolling for large datasets.
  • Defer non-critical UI.
  • Build using production configuration.
  • Measure performance before optimizing.
  • Continuously monitor Core Web Vitals.

Advantages

Technique Benefit
Signals Fine-grained updates
OnPush Reduced Change Detection
Lazy Loading Faster startup
Virtual Scrolling Lower memory usage
SSR Better SEO
Hydration Faster interaction
Deferrable Views Improved Core Web Vitals
Async Pipe Cleaner RxJS usage

Top 10 Angular Performance Optimization Interview Questions

1. What are the most important Angular performance optimization techniques?

Answer

Use Lazy Loading, Standalone Components, OnPush Change Detection, Signals, Computed Signals, Virtual Scrolling, trackBy, Deferrable Views, SSR, Hydration, and RxJS best practices.


2. Why is OnPush faster?

Answer

OnPush reduces unnecessary Change Detection by checking components only when specific triggers occur, such as input reference changes, template events, Signal updates, Async Pipe emissions, or manual marking.


3. How do Signals improve performance?

Answer

Signals provide fine-grained dependency tracking so Angular updates only the parts of the UI that depend on the changed Signal.


4. Why should trackBy be used?

Answer

trackBy allows Angular to reuse existing DOM elements instead of recreating them, improving rendering performance for large lists.


5. What is Virtual Scrolling?

Answer

Virtual Scrolling renders only the visible items in a large list, reducing memory usage and improving scrolling performance.


6. What are Deferrable Views?

Answer

Deferrable Views (@defer) delay rendering of non-critical content until it is needed, reducing the initial rendering cost.


Answer

They simplify application structure, improve tree shaking, reduce bundle size, and work well with modern Angular features.


8. What is the role of SSR and Hydration?

Answer

SSR improves SEO and initial page load by rendering HTML on the server. Hydration makes the server-rendered HTML interactive without recreating the DOM.


9. What are RxJS performance best practices?

Answer

Use the Async Pipe, debounce user input, cancel stale requests with switchMap, avoid nested subscriptions, and unsubscribe appropriately when not using the Async Pipe.


Answer

Use Standalone Components, Lazy Loading, OnPush Change Detection, Signals for UI state, Computed Signals for derived values, RxJS for asynchronous operations, Virtual Scrolling for large datasets, Deferrable Views for non-critical content, and SSR with Hydration for optimal rendering.


Interview Cheat Sheet

Requirement Recommended Solution
Local UI State Signals
Derived State computed()
Async Operations RxJS
Large Lists trackBy + Virtual Scrolling
Change Detection OnPush
Lazy Features Lazy Loading
Initial Render @defer
SEO SSR
Faster Interactivity Hydration
Production Deployment Production Build

Summary

Angular performance optimization is achieved by combining multiple techniques rather than relying on a single feature. Standalone Components, Lazy Loading, OnPush Change Detection, Signals, Computed Signals, Virtual Scrolling, Deferrable Views, SSR, Hydration, and RxJS optimization together create applications that load quickly, render efficiently, and scale well. Measuring performance with real metrics and applying optimizations where they provide value is the key to building enterprise-grade Angular applications.


Key Takeaways

  • ✔ Prefer Standalone Components for new Angular applications.
  • ✔ Lazy-load feature areas to reduce initial bundle size.
  • ✔ Use OnPush for reusable feature components.
  • ✔ Use Signals for local reactive UI state.
  • ✔ Use Computed Signals for derived values.
  • ✔ Add trackBy for large lists.
  • ✔ Use Virtual Scrolling for large datasets.
  • ✔ Defer non-critical UI with @defer.
  • ✔ Combine SSR and Hydration for better SEO and startup performance.
  • ✔ Profile your application and optimize based on measured bottlenecks.

Next Article

➡️ 93-Lazy-Loading-QA.md