In this tutorial, you will learn:
- What are Signals and Observables
- Why need to migrate from Observables to Signals
- Step-by-step migration examples
- What are the best practices for Angular developers
Introduction
Nowadays, Angular developers use Signals to manage reactive state, while traditionally, developers mostly used RxJS Observables for asynchronous data and state management.
What are Observables in Angular?
Observables come from RxJS, and it is used to handle asynchronous operations like:
- API responses
- User events
- Real-time data
Example using Observable:
import { Observable, of } from 'rxjs';
data$: Observable = of('Hello World!');
To display data in Angular templates:
{{ data$ | async }}
What are Signals in Angular?
Signals are a reactive state management feature that automatically updates the UI when the value changes.
Example:
import { signal } from '@angular/core';
data = signal('Hello World!');
Display data in HTML
{{ data() }}
Observables vs Signals
| Feature | Observables | Signals |
|---|---|---|
| Library | RxJS | Angular Core |
| Complexity | Medium to High | Simple |
| Data type | Stream of values | Reactive state |
| Template usage | async pipe | direct function call |
| Performance | Good | Faster change detection |
Why need to migrate Observables to Signals?
There are many reasons to migrate from Observables to Signals
1. Simpler State Management
Signals remove the need for complex RxJS operators.
2. Better Performance
Signals are used for better Performance.
3. Cleaner Code
Less boilerplate compared to RxJS subscriptions.
Example: Migrating Observable to Signal
Step 1: Simple Observable Example
import { Component } from '@angular/core';
import { of } from 'rxjs';
@Component({
selector: 'app-example',
template: `{{ data$ | async }}`
})
export class ExampleComponent {
data$ = of('Hello Data');
}
Step 2: Convert Observable to Signal
import { Component, signal } from '@angular/core';
@Component({
selector: 'app-example',
template: `{{ data() }}`
})
export class ExampleComponent {
data = signal('Hello Data');
}
Use Signal into HTTP Observable
Angular HTTP calls return Observables by default.
Simple Example:
this.http.get('/api/users')
.subscribe(data => {
this.users = data;
});
Use Signal in Example
users = signal([]);
this.http.get('/api/users')
.subscribe(data => {
this.users.set(data);
});
Using toSignal() for Migration
Angular has a function toSignal() to convert Observables into Signals.
Example:
import { toSignal } from '@angular/core/rxjs-interop';
users = toSignal(this.http.get('/api/users'));
Now you can show users in a template
{{ users() | json }}
When You Should NOT Replace Observables
You should not replace Observable when using below things
1. API calls
2. Event streams
3. Complex async logic
Note: You should use Signal in UI state only.
Common Migration Mistakes
❌ Replacing Observables from API call, Event streams, etc.
❌ Mixing subscriptions and signals incorrectly.
❌ Not using toSignal() helper.
Conclusion
RxJS Observables are used for asynchronous operations, while Angular Signals are ideal for managing UI state.