Process substitution in bash

2 min read

This post is part of my Today I learned series in which I share all my learnings regarding web development.

Today I came across this little snippet of shell code bash <(curl -s https://codecov.io/bash). I found it in the documentation of Codecov which is a code coverage tool mainly run in CI.

This "command structure" bash <(...) was completely new to me. So I digged a little bit.

What you see there is called process substitution and the definition of it is as follow:

Process substitution allows a process’s input or output to be referred to using a filename.

Huh – that's interesting. So let's give this a try.

$ echo <(ls .)
/dev/fd/11

Okay, this is clearly a file name. Let's try something else and have a look into the file using cat.

$ cat <(ls .)
README.md
assets
...
...

Interesting this works and shows the files that are in the current working directory.

Side note: I still have to dig what this /dev/fd folder is used for because there are a lot of interesting things like stdout@, stdin@ and stderr@ in there, but this is another topic.

So what does this mean?

<(...) lets you use the ouput of a command, where you would normally need a file. (thx to crater2150 for this understandable explanation on stack overflow)

And this can become quite handy if you want to "pipe" something into a command that doesn't understand pipes. So what happens in the codecov example above is, that a bash script is downloaded from https://codecov.io/bash, the content is written to a file and bash then executes this file. Pretty cool, hmm?

In a Node.js context you could use it like this:

$ node <(echo 'console.log("foo")')
foo

But even cooler you could use process substitution to quickly execute stuff from e.g. the clipboard. I'm on a Mac which means that I have the pbpaste command available.

$ node <(pbpaste)

These few lines will execute anything I have in my clipboard in Node.js. No more temporary files! 🎉

Tags

Load time