No history yet

Introduction to RxJS

Handling Asynchronous Events

In JavaScript, we often deal with asynchronous events, like a user clicking a button, an API returning data, or a timer finishing. These don't happen all at once. They arrive over time, creating a stream of events.

RxJS, which stands for Reactive Extensions for JavaScript, is a library designed to handle these streams. Think of it as a toolkit for composing asynchronous and event-based programs. Instead of dealing with callbacks or promises one at a time, RxJS lets you treat events as a collection you can filter, combine, and transform, much like you would with an array.

Observables: The Core Concept

The foundation of RxJS is the Observable. An Observable is a blueprint for a stream of values that will arrive over time. It can emit multiple values, a single value, or none at all. It can also signal an error or completion.

Imagine an Observable as a newsletter you can subscribe to. It doesn't send out anything until someone signs up. Once you subscribe, you start receiving issues (data) as they're published. This lazy nature is key; an Observable only starts its work when it has a listener.

Here’s how you can create a simple Observable that emits the numbers 1, 2, and 3 in sequence, and then completes.

import { Observable } from 'rxjs';

const myObservable = new Observable(subscriber => {
  subscriber.next(1);
  subscriber.next(2);
  subscriber.next(3);
  subscriber.complete();
});

This code defines an Observable, but it doesn't run yet. To get the values, we need something to listen to it.

Observers and Subscriptions

An Observer is the listener. It's an object with up to three methods: next(), error(), and complete().

  • next(value): Called whenever the Observable emits a new value.
  • error(err): Called if the Observable encounters an error.
  • complete(): Called when the Observable has no more values to emit.

To connect an Observer to an Observable, you use the .subscribe() method. This action kicks off the Observable's execution and returns a Subscription object.

// This is our Observer
const myObserver = {
  next: x => console.log('Value received: ' + x),
  error: err => console.error('Observer got an error: ' + err),
  complete: () => console.log('Observer got a complete notification'),
};

// This kicks off the Observable's execution
const subscription = myObservable.subscribe(myObserver);

// Console output:
// Value received: 1
// Value received: 2
// Value received: 3
// Observer got a complete notification

The Subscription object is important. It represents the ongoing execution and has an unsubscribe() method. Calling this method stops the listener from receiving further notifications and allows for garbage collection, preventing memory leaks. It's like canceling your newsletter subscription.

subscription.unsubscribe();

Transforming Streams with Operators

Operators are the real power of RxJS. They are pure functions that take an Observable as input and create a new Observable as output. This allows you to chain operators together to create complex data processing pipelines.

Think of a factory assembly line. The raw material (the initial Observable stream) goes in one end. Each station on the line (an operator) modifies it in some way before passing it to the next. The pipe() method is how you connect these stations.

Lesson image

For example, let's say we have a stream of numbers. We only want the even ones, and we want to square them. We can use the filter and map operators to do this.

import { of } from 'rxjs';
import { filter, map } from 'rxjs/operators';

const numbers$ = of(1, 2, 3, 4, 5); // A simple way to create an Observable

numbers$.pipe(
  filter(n => n % 2 === 0), // Only let even numbers pass through
  map(n => n * n)           // Square the remaining numbers
).subscribe(x => console.log(x));

// Console output:
// 4
// 16

RxJS offers dozens of operators for everything from filtering and transformation to error handling and combining multiple streams.

Now, let's test your understanding of these core concepts.

Quiz Questions 1/5

What is the primary role of an Observable in RxJS?

Quiz Questions 2/5

True or False: An Observable begins emitting values as soon as it is created.

Understanding Observables, Observers, and Operators is the first step to mastering reactive programming with RxJS. These building blocks allow you to manage complex asynchronous code in a clear and declarative way.