Living in the terminal


Why bother becoming proficient in the command line? As a developer, it’s a great skill to have because it boosts your productivity. Sure, you might be able to click some buttons in a GUI to accomplish the same task, but for most things (and it’s more than you might think, as we will soon see), save for editing photos, it’s far faster to type a few terminal commands (after the initial learning curve).

Some background

Throughout my childhood, I played around with computers, trying to figure out how it’s possible for just about anything to appear on the screen with a few clicks. This happened on Windows XP, then Vista, then 7, 8, 10.

Around middle school, I decided to try Linux, but I have no recollection of what caused me to discover it in the first place. I probably read about it and thought “wait a second, I can install something like Windows on the computer, but it’s not Windows?” Excited by the discovery, I found the nearest blank CD and burned my first ISO. It was Ubuntu, probably 11.04.

Since then, I’ve used various iterations of Ubuntu, Linux Mint, Xubuntu, and most recently Debian, dual-booting with Windows early on. Around four years ago, I nuked the Windows partition.

I have spent the most time (about two years) using my current setup, which is Debian without a desktop environment (I use dwm for the window manager). For the vast majority of people, including me, using a window manager induces copious amounts of yak shaving. This is especially true when dealing with desktop applications that were design in the context of a desktop environment. Don’t ask me how long it took to find out that to get IntelliJ IDEA to render properly, I had run to wmname LG3D in the terminal.

Speaking of the terminal, let’s get to what I really wanted to talk about. After I switched to dwm, my usage of the terminal increased exponentially, and so did my exposure to problems that required me to take full advantage of what a Unix environment has to offer.

Terminal, console, shell, command line?

You may have heard all of these words. Each means something a little different. This explanation does a great job of breaking down the terminology, and andcoz’s answer provides a succinct summary: “when you look to a “text window” on your linux system (under X11) you are looking to: a terminal emulator, connected to a virtual terminal, identified by a tty file, inside which runs a shell.”

Understanding these differences will prevent confusion in the future if you’re serious about stepping up your command line game. Even more importantly, knowing these fundamentals will allow you to solve novel problems that haven’t yet been answered in a Stack Exchange post.

But I can’t do X in the terminal

I thought the same thing at first. But after finding out that writing integers to /sys/class/backlight/intel_backlight/brightness can change my laptop’s screen brightness, I thought differently.

The following examples may or may not work out the of box depending on your Linux distribution. If a command doesn’t work, it takes only one command to install the new command. The same goes for macOS.

For example, did you know that you have a calculator on hand with bc?

john@thinkpad ~ $ bc
bc 1.07.1
2 + 2
4587 * 344
343 % 32
8 / 0
Runtime error (func=(main), adr=5): Divide by zero

Need to know the time and date?

john@thinkpad ~ $ date
Sun 26 Apr 2020 05:33:43 PM CDT

Oh, and if you want to put that date on a calendar:

john@thinkpad ~ $ cal
     April 2020
Su Mo Tu We Th Fr Sa
          1  2  3  4
 5  6  7  8  9 10 11
12 13 14 15 16 17 18
19 20 21 22 23 24 25
26 27 28 29 30

(Copying the output to this blog does not show all formatting—there’s a highlight on the current day.)

Connect to Bluetooth devices using bluetoothctl, store your passwords with pass, and even check the weather while you’re at it.

john@thinkpad ~ $ curl
Weather report: sf

    \  /       Partly cloudy
  _ /"".-.     64 °F
    \_(   ).   → 17 mph
    /(___(__)  9 mi
               0.0 in
┌──────────────────────────────┬───────────────────────┤  Sun 26 Apr ├───────────────────────┬──────────────────────────────┐
│            Morning           │             Noon      └──────┬──────┘     Evening           │             Night            │
│     \   /     Sunny          │     \   /     Sunny          │     \   /     Sunny          │    \  /       Partly cloudy  │
│      .-.      53..55 °F      │      .-.      57..59 °F      │      .-.      55..57 °F      │  _ /"".-.     51..55 °F      │
│   ― (   ) ―   → 8-12 mph     │   ― (   ) ―   → 12-18 mph    │   ― (   ) ―   → 15-24 mph    │    \_(   ).   → 11-21 mph    │
│      `-’      6 mi           │      `-’      6 mi           │      `-’      6 mi           │    /(___(__)  6 mi           │
│     /   \     0.0 in | 0%    │     /   \     0.0 in | 0%    │     /   \     0.0 in | 0%    │               0.0 in | 0%    │

Location: SF, California, United States of America [37.7792808,-122.4192362]

Okay, maybe some of these are fun, but don’t really affect your productivity as a developer.

Let’s look at a couple that do.

Have a text file whose contents you want to copy onto the clipboard? You could open a file explorer, double-click on the file, select all the text, copy, and then close the editor window. Or you could do this:

cat file.txt | xclip -selection clipboard

Maybe you feel that a project is taking up too much space on your hard drive, and you need a way to tell what directories and files are at fault. ncdu is an interactive version of du (disk usage) that allows you to browse the file system with the largest directories sorted to the top by default. It even gives a relative size indicator next to each file or directory.

split -d -l 50 large.txt part_ will split large.txt into many small text files, placing 50 lines in each. The output files will be named part_1, part_2, part_3, and so on. Imagine how long it would take to do that by hand if large.txt contained 5000 lines!

Each program usually comes with a man (manual) page that you can display by doing something like man cal or man split. You’ll find that each program provides options that allow you to tweak the output. For example, maybe you want a whole year’s calendar, or maybe you want split up the file into files of no more than n bytes instead of splitting based on lines.


There are many more tools than the ones I have listed.

The next time you’re faced with an extremely tedious, nearly impossible task, like renaming thousands of files according to a pattern and then replacing a certain string across all of them, see if you can do it using a few shell commands.

Don’t waste time on repetitive tasks. Learn to automate, and do it relentlessly.

Suppose you have some task that takes a couple hours. It might take an entire day to create a series of commands or a shell script that automates the task, but if it’s a recurring task, the investment of one day upfront will pay massive dividends.

Found a mistake? Edit this post.