Skip to content

How to unsubscribe from Observable in Angular

When working with Observables in Angular, it’s important to unsubscribe from them to prevent memory leaks.

In this article, I’ll show you 4 different ways to unsubscribe from an Observable in Angular.

Using unsubscribe() method in ngOnDestroy hook

You can manually unsubscribe from an Observable in the ngOnDestroy() lifecycle hook:

import { Component, OnDestroy } from '@angular/core';
import { Subscription } from 'rxjs';

@Component({
  selector: 'app-example',
  templateUrl: './example.component.html',
})
export class ExampleComponent implements OnDestroy {
  subscription: Subscription;

  ngOnInit() {
    this.subscription = this.myService.getData().subscribe(data => {
      console.log(data);
    });
  }

  ngOnDestroy() {
    // Unsubscribe to prevent memory leaks
    this.subscription.unsubscribe();
  }
}

The async pipe automatically handles subscription and unsubscription, so you don’t need to unsubscribe manually. This is especially useful when displaying data in templates.

<div *ngIf="data$ | async as data">
  {{ data }}
</div>
@Component({
  selector: 'app-example',
  templateUrl: './example.component.html',
})
export class ExampleComponent {
  data$ = this.myService.getData();
}

This method is useful when you have multiple Observables and want to unsubscribe from all of them in one place. You use a Subject to emit a value when the component is destroyed.

import { Component, OnDestroy } from '@angular/core';
import { Subject } from 'rxjs';
import { takeUntil } from 'rxjs/operators';

@Component({
  selector: 'app-example',
  templateUrl: './example.component.html',
})
export class ExampleComponent implements OnInit, OnDestroy {
  private destroy$ = new Subject<void>();

  ngOnInit() {
    this.myService.getData()
      .pipe(takeUntil(this.destroy$))
      .subscribe(data => {
        console.log(data);
      });
  }

  ngOnDestroy() {
    this.destroy$.next();
    this.destroy$.complete();
  }
}

Using take or first Operator

If you only need one value from the Observable, you can use the take(1) or first() operator to automatically complete the subscription after one emission.

import { Component } from '@angular/core';
import { take } from 'rxjs/operators';

@Component({
  selector: 'app-example',
  templateUrl: './example.component.html',
})
export class ExampleComponent implements OnInit {
  ngOnInit() {
    this.myService.getData()
      .pipe(take(1))
      .subscribe(data => {
        console.log(data);
      });
  }
}