RxJS 7 and Beyond: What to Expect and Prepare For
Originally published at labs.thisdot.co
Nov 30, 2020 · 5 minutes read · Follow @luixaviles
Some days ago I’ve been part of the Modern Web Podcast along with Tracy Lee and we interviewed to Ben Lesh, the author of RxJS(A JavaScript library for reactive programming using Observables), on the most recent updates for RxJS 7 and it’s targeted release date.
It was an opportunity to understand how RxJS has been improved over time, how TypeScript helped to identify bugs and improved the project itself.
It worths mentioning that RxJS 7 has been around a year now. Actually, the v7 alpha was released a year ago and the first beta came out 7 months ago. Let’s discover the upcoming features and breaking changes.
Better TypeScript typings
This is the biggest improvement for this latest version. Giving these updates required some breaking changes into the library. However, the team is proud to provide better type inference now.
toPromise Operator
Let’s see an example with .toPromise
operator for better understanding:
const values = ['a', 'b', 'c', 'd', undefined];
const result: string = await from(values).toPromise();
console.log(result); // prints 'undefined'
The Promise API ensures getting a result(fulfilled) or an error(rejected). However, with .toPromise
operator it’s possible to get undefined
if the observable completes without emitting any value or that value was emitted last and it won’t throw any error.
With RxJS 7, you’ll need to specify undefined
along with the union type of TypeScript:
const values = ['a', 'b', 'c', 'd', undefined];
const result: string | undefined = await from(values).toPromise(); // Promise<T | undefined>
console.log(result); // prints 'undefined'
As an important note about it, the .toPromise
operator will be deprecated in RxJS 7 and it will be removed by RxJS 8. In its place, you’ll find firstValueFrom()
and lastValueFrom()
firstValueFrom
This function subscribes to an Observable and converts it to a promise. The promise result will be resolved as soon as the first value arrives from the observable and then the subscription will be closed.
const values = ['a', 'b', 'c', 'd'];
const observable = from(values);
const result: string = await firstValueFrom(observable); // Promise<string>
console.log(result); // prints 'a'
As consequence, this operator should be used when you know the observable will emit at least one value.
lastValueFrom
This function converts an Observable to a promise by subscribing to the observable and waiting for it to complete. The promise will resolve the last value from the stream.
const values = ['a', 'b', 'c', 'd'];
const observable = from(values);
const result: string = await lastValueFrom(observable);
console.log(result); // prints 'd'
Of course, this operator should be used only when you know the observable will complete any time. Otherwise, you end pu with a promise that is hung up.
RxJS is smaller
Not too many words are needed to describe this awesome improvement. However, in the last couple of months of work the RxJS team done a lot of code refactoring that reduced the size drastically. In the words of Ben Lesh, it’s now almost 50% smaller.
A lot of these improvements were done through code refactoring. The original code was written 6 years ago and there’s been like 4 rewrites that Ben created with experimental branches but they never ever made it over. Most of these changes were sent as refactor: smallify all the things Pull Request.
RxJS supports the latest TypeScript version
The RxJS team was waiting for TypeScript 4 for code refactoring and now that v4.1 is coming there are a couple of features they may want to use. Mostly for better type inference and bad types fixing.
Stability Matters
The RxJS team is focusing on getting those changes as stable as possible. This has a high priority having in mind the 23+ Million downloads per week of the library.
On other hand, Google syncs their codebase(their entire huge mono repository) with the master branch of RxJS. Thus, RxJS 7 has been used in production for a while by Google products.
How TypeScript improved RxJS?
It’s an interesting fact to know that the RxJS project is using TypeScript actively, in the words of Ben Lesh:
TypeScript is awesome. When RxJS migrated from JavaScript to TypeScript we found bugs immediately(it was in TypeScript 1.8). RxJS implementation is using all of the stricter settings for TypeScript, We’re trying to be strict as possible and I recommend that too by the way.
If you’re building an App that uses libraries, TypeScript would be a great addition for you(talking about the Developer Experience) and your project. You should put in strict settings and get everything to work.
It is worth mentioning that the TypeScript team has added a lot of features because of Angular and RxJS projects too.
RxJS 7 and Beyond
It looks like at this point the version 8 will not need to be a complete rewrite. RxJS 8 will just go through the pending deprecations and finally get rid of them, mainly because a lot of them were sitting there for about 2 years. Of course, these changes would reduce the size of the library a lot more and will make it smaller and faster.
What about RxJS 9 or even future versions?
Ben explained that some libraries and APIs started using the AbortSignal interface. It can be used currently with fetch as a cancellation primitive:
const controller = new AbortController();
const signal = controller.signal;
function fetchResource() {
fetch(url, { signal })
.then((response) => {
// process the response here
})
.catch((e) => {
console.log('Error', e);
});
}
function cancel() {
controller.abort();
}
This API exists in the browser and will be available in Node.js. RxJS would probably want to use the same cancellation mechanism. However, this is speculation for now because nothing like that will be done very quickly.
RxJS is an Open Source project
There is a lot of exciting news around RxJS. So, why is actually taking some time to have v7 ready? Ben explained that there’s a couple of issues that need to be solved before the release of the stable version.
Also, it is difficult to set a fixed date for the expected release since these improvements and fixes are all about volunteer work.
If you are interested to contribute with your TypeScript skills, please come and help to RxJS team!
You can follow me on Twitter and GitHub to see more about my work.