Make every program a filter.
Mike Gancarz, The UNIX Philosophy
It's no secret that I love working with GNU/Linux. The ease that I get at my fingers is uncanny and like no other. I don't even have to touch my mouse most of the time.
In this blog, I would like to talk about how I use GNU tools and utilities, and how it helps me get work done efficiently and quickly.
The problem
I have 2 scripts:
xx-print-emoji.sh: This script takes an emoji name and prints an emoji. For example:
$ xx-print-emoji.sh red_circle
๐ด
$ xx-print-emoji.sh yellow_circle
๐ก
xx-show-emoji-names.sh: This script prints all the emoji names in Unicode as a list (downloaded and cached) from the Unicode website. Printing the first 10 results yields:
$ xx-show-emoji-names.sh | head
grinning face
grinning face with big eyes
grinning face with smiling eyes
beaming face with smiling eyes
grinning squinting face
grinning face with sweat
rolling on the floor laughing
face with tears of joy
slightly smiling face
I want to print the globe emoji in my blog text; how can I use GNU tools to get me what I want?
The solution
Let's go through the steps I took:
Step 1: Search for globe in xx-show-emoji-names.sh
results:
$ xx-show-emoji-names.sh | grep globe
globe showing Europe-Africa
globe showing Americas
globe showing Asia-Australia
globe with meridians
Step 2: Remove spaces from the results to make it suitable as an input for xx-print-emoji.sh
:
$ xx-show-emoji-names.sh | grep globe | sed -e "s/\s/_/g"
globe_showing_Europe-Africa
globe_showing_Americas
globe_showing_Asia-Australia
globe_with_meridians
Step 3: Convert -
to _
for all results, further making it suitable for xx-print-emoji.sh
:
$ xx-show-emoji-names.sh | grep globe | sed -e "s/\s/_/g" | sed -e "s/-/_/g"
globe_showing_Europe_Africa
globe_showing_Americas
globe_showing_Asia_Australia
globe_with_meridians
Step 4: Try the each result with xx-print-emoji.sh
:
$ xx-print-emoji.sh $(xx-show-emoji-names.sh | grep globe | sed -e "s/\s/_/g" | sed -e "s/-/_/g" | sed -n "1p")
$ xx-print-emoji.sh $(xx-show-emoji-names.sh | grep globe | sed -e "s/\s/_/g" | sed -e "s/-/_/g" | sed -n "2p")
๐
$ xx-print-emoji.sh $(xx-show-emoji-names.sh | grep globe | sed -e "s/\s/_/g" | sed -e "s/-/_/g" | sed -n "3p")
$ xx-print-emoji.sh $(xx-show-emoji-names.sh | grep globe | sed -e "s/\s/_/g" | sed -e "s/-/_/g" | sed -n "4p")
๐
Bingo! The last emoji is the one I'm looking for!
The bottom line
Wealth gotten by vanity shall be diminished: but he that gathereth by labour shall increase.
Proverbs 13:11, The Bible
A couple takeaways:
- Notice how I used
|
to pipe two commands together. This feature is one of GNU's most powerful features! Every command's output can be treated as the input of another command. Every appended command can then filter the results of the previous command. This pipe-and-filter framework is what makes using Linux a breeze. - I only used grep and sed in this blog, but there are many others like sort, unique, more, less etc. All these tools have different purposes but can be piped in the same way.
- I could create my own script or program that uses piping in the exact same way. This modularity makes it easy to extend functionality in the future, even for unpredicted scenarios.
- I don't have to learn a new program, or worse, learn a new user interface for the same old program. I could just use what's available on my computer.
- GNU tools take very little space on my computer but offer infinite value.
- It puts bigger applications to shame. They all use far more memory and some run slower than GNU tools.