RxJS Mastery- #9 EMPTY

Why is EMPTY uppercase in this post? All other concepts explained in the previous lessons were lowercase. This is because the RxJS empty operator is deprecated. It will be replaced by the EMPTY constant (or by scheduled) with RxJS version 8.

RxJS EMPTY constant explained 🎓

The EMPTY constant is the same as the deprecated operator empty() without a scheduler argument. It returns or represents an Observable instance. This Observable just completes and does nothing else.

So, the following code will just output ‘Complete!’:

EMPTY.subscribe({
    next: () => console.log('Next'),
    complete: () => console.log('Complete!')
});

What problems does the RxJS EMPTY constant solve? 🚧

EMPTY is usually used together with other operators. It comes in handy if you have a condition where you don’t want to emit a value in some cases. In the following example only in case of odd numbers a next notification is emitted with a value:

const interval$ = interval(1000);
const result = interval$.pipe(
    mergeMap(x => x % 2 === 1 ? of('a', 'b', 'c') : EMPTY),
);
result.subscribe(x => console.log(x));

How to test the EMPTY constant🚦

The interval in the test below is emitting a number each millisecond. MergeMap afterwards only maps the odd numbers. In the case of an even number it just maps and flattens EMPTY. This means in the even number case just some time passes without emission. This we can elegantly test with marbles testing by using ‘-‘.

it('should be testable with marbles', () => {
    testScheduler.run((helpers) => {
        const { expectObservable } = helpers;
        const interval$ = interval(1);
        const result$ = interval$.pipe(
            mergeMap(x => x % 2 === 1 ? of(x) : EMPTY),
            take(3)
        );

        expectObservable(result$).toBe('--a-b-(c|)', {a: 1, b: 3, c: 5});
    });
});

The take(3) operator just ensures that our Observable and test completes after 3 values are emitted. This again shows that EMPTY does not emit any value via next notification but just completes.

Furthermore, the EMPTY constant could also be helpful if you want to fail silently. In an error case you can just return EMPTY. But this is not a good idea in all cases. Usually the Observer wants to know and handle error cases.

Exercise for the EMPTY constant 💪

Execute a request with the help of ajax. In an error case just complete the Observable without error notification.