Process substitution in bash
- Published at
- Updated at
- Reading time
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 <(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
stderr@ in there, but this is another topic.
So what does this mean?
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! 🎉