Custom software development & design company

Home

Services

What We Do

View projects we have done

Works

Mobile apps
Mobile apps Need an estimate?

Contact Us

Mobile apps JSGuru's story

About Us

Certifications and awards

Awards

Learn what it is like to work in JSGuru

Careers

Read our

Blog

scroll down

Javascript Pipeline Operator

Bojan Gvozderac

Author at JSGuru

I’m back at it again with my functional programming shenanigans and this time I’m going to talk about PIPES!

Yes, PIPES!

We use them in the most important piece of hardware in any building — the mighty toilet and now also in our software development! 

Truly a testament to the versatility of the proud PIPE!

Preface

In a blog post about functional programming I wrote before ( LINK ) I showed you an example:

const compose = (...fns) => x => fns.reduceRight((v, f) => f(v), x);

With this ( partial ) explanation:

After that we reduceRight the array of gathered functions with the initial value — x, this is the same as reduce but starts at the end of the array and moves to the start because that is how ‘compose’ works if the opposite is more natural to you than you want to pipe functions.

Well it turns out JavaScript liked that code up there so much that they decided to give it it’s very own operator but with a twist. 

They liked the “more natural” approach of piping functions instead of composing them and that’s how we got the Pipeline operator and it looks like this |> 

I know what you’re thinking… ugly mofo but nevertheless very useful when coding functionally as we’ll soon find out.

One thing to note here: Pipeline operator is currently at Stage 1 and is not part of the ECMAScript specification yet but I’m such a functional programming nerd I couldn’t pass up the opportunity to talk about the shiny new thing in FP JavaScript

The Obligatory MDN Section

Since I can’t take a dumb without looking it up on MDN ( big love MDN ) we’re gonna take a look at what it says for pipeline operator

The experimental pipeline operator |> (currently at stage 1) allows the creation of chained function calls in a readable manner. Basically, the pipeline operator provides syntactic sugar on a function call with a single argument allowing you to write

Example from MDN:

const double = (n) => n * 2;
const increment = (n) => n + 1;

// without pipeline operator
double(increment(double(double(5)))); // 42

// with pipeline operator
5 |> double |> double |> increment |> double; // 42

So that’s pretty cool and makes it really easy to understand how the data flows and transitions from the starting “5” to “42” at the end.

The result is code that is much easier to read and comprehend!

Bringing it All Together

So how does the pipeline operator tie in with our “compose” function above?

I’m glad I asked me because this is how I’d go about it:

First to refactor the compose function in to pipe

const pipe = (...fns) => value => fns.reduce((argument, func) => func(argument), value);

Now for some example usage

const double = number => number * 2;
const increment = number => number + 1;
const doubleThenIncrement = pipe(double, increment);
log(
  'Result of doubling then incrementing "4"',
  doubleThenIncrement(4)
);

Now that we have the functionality let’s refactor to use the new pipeline operator

const pipe = (...fns) => value => fns.reduce((argument, func) => argument |> func, value);

Finally, let’s refactor our example

const double = number => number * 2;
const increment = number => number + 1;
const doubleThenIncrement = pipe(double, increment);
log(
  'Result of doubling then incrementing "4"',
  4 |> doubleThenIncrement
);

And there we have it!

A simple upgrade that makes the whole process of doubling then incrementing a number much more readable and the best part is that it gets more and more readable the more you use it (eventually… the whole being at stage 1 thing is really throwing a wrench in our cleaner code works for now ).