An Observably-More-Useful Data Type

Once upon a time, computers had only room for a single value — the Integer. Then one day, someone said — What if you could use that single Integer to choose another integer from a larger set of integers? Thus the Array was born. And computing has never been the same.

Okay, so it didn’t happen exactly that way :) But the point is that the birth of a data type can be a revolutionary event for programmers. And a new data type is here that we cannot ignore: the Observable.

The Smartest Async Option

Consider a query to GitHub for all users on a repo:

const response = query(usersForRepo, {repoId: '123'}

What do you think the response object is, and how would you expect to consume it?

  1. It’s an Array — pass a function to forEach to iterate over it.
  2. It’s a Promise — pass a function to then which receives and iterates over the array.
  3. It’s a Promise — pass a function to then which resolves to an object, from which you’ll pull the data field, then iterate over the array.
  4. It’s an Observable — pass a function to subscribe to iterate over each user in the array.

You might know that 1) is incorrect because GitHub is a remote server. And we know that we can’t simply iterate over something that is not available right away.

You might be thinking 2) or 3) is good, depending on whether you use GraphQL or REST. And you might never have worked with style number 4) unless you have used Rx, or Observables. But that’s why you need to pay attention to number 4). This final style returns a data type called Observable which is powerful because:

  1. It is more concise then having a callback for iteration inside of a callback for async resolution.
  2. It requires no code change even if the remoteArray is a local array

First, note its similarity to iterating over a local array:

- localArray.forEach(addUserToUI)
+ localArray.subscribe(addUserToUI)

This removal of indirection is not only cosmetic — that’s the least of its benefits. The real bonus is that it raises the level at which we think about what the response is.

I call an endpoint, expecting an iterable of users

vs

I call an endpoint, expecting a transport object containing my users.

Operational Benefits

Now, let’s rule out option 1), and study the remaining 3 options in a few timing and error handling scenarios — in other words, the operational aspects of the code.

  1. Server moves to a Streaming Response

If your code waits for an entire object to be returned and parsed, then it cannot run any `addUserToUI` callbacks before the entire response has loaded so it gets no benefit from streaming. However, if your code works with an Observable of users, it may be able to run some of your callbacks sooner to take advantage of streaming. Forgoing the benefits of streaming responses, in this world of mobile, often spotty connections, is a Very Bad Idea.

2) Server has an error upon retrieving the third record

Because Observables can work over streaming connections, they may be able to have displayed the first two users, even if an error occurred. Because of Observable-based methods such as `retry()` as implemented by RxJS, the refetching of the data might be done with a minimal impact to the calling code. Ignoring the probability of failure, in this distributed era, is a Very Bad Idea as well.

3) Server is able to live-stream users to the client as they join the repo

These days, streaming options are proliferating, such as MeteorJS, FeathersJS and GraphQL , which allow clients to subscribe to, and be pushed updates. While streaming servers are not yet everywhere, their growth is not in doubt. If your users-for-repo query returns an Observable, and the right plumbing is in place, you can have a live-updating UI with no additional work. Maybe you need this today; maybe you don’t. But having an abstraction that supports it is strategic. Ignoring the rapid rate of change in the JS world is something we do at our own peril.

Observably Better

In conclusion — Observable is a powerful new data-type, ideal for the distributed-systems era. It’s powerful enough that Netflix and Google are building around it (and as a contractor, I’m also putting my clients on it). Since nearly every developer these days does distributed systems async programming, the benefits of a common abstraction can help us all.

Your investment in learning Observables will be well spent. I know folks using them in Java, .Net, Swift.. Pro-tip — get going to the ReactiveX website and read more today! Your code will improve — observably.

Dean Radcliffe
Deanius Solutions, Inc.

One clap, two clap, three clap, forty?

By clapping more or less, you can signal to us which stories really stand out.