This chapter contains a few little extra commands that I think are both fun and useful. Some are not available on all systems, but hopefully they’ll be available on yours.
Try combining some of these commands with other commands in this book to create new workflows.
If you spend your life living in a terminal window, the cal command can be quite useful for helping you check dates.
The basic usage of cal will print out the current month’s calendar, as seen in Listing 9.1.
$ cal
December 2013
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 31
If you need to see the current year’s calendar at a glance, the -y flag will print the full year’s calendar.
$ cal -y
2013
January February March
Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa
1 2 3 4 5 1 2 1 2
6 7 8 9 10 11 12 3 4 5 6 7 8 9 3 4 5 6 7 8 9
13 14 15 16 17 18 19 10 11 12 13 14 15 16 10 11 12 13 14 15 16
20 21 22 23 24 25 26 17 18 19 20 21 22 23 17 18 19 20 21 22 23
27 28 29 30 31 24 25 26 27 28 24 25 26 27 28 29 30
31
April May June
Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa
1 2 3 4 5 6 1 2 3 4 1
7 8 9 10 11 12 13 5 6 7 8 9 10 11 2 3 4 5 6 7 8
14 15 16 17 18 19 20 12 13 14 15 16 17 18 9 10 11 12 13 14 15
21 22 23 24 25 26 27 19 20 21 22 23 24 25 16 17 18 19 20 21 22
28 29 30 26 27 28 29 30 31 23 24 25 26 27 28 29
30
July August September
Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa
1 2 3 4 5 6 1 2 3 1 2 3 4 5 6 7
7 8 9 10 11 12 13 4 5 6 7 8 9 10 8 9 10 11 12 13 14
14 15 16 17 18 19 20 11 12 13 14 15 16 17 15 16 17 18 19 20 21
21 22 23 24 25 26 27 18 19 20 21 22 23 24 22 23 24 25 26 27 28
28 29 30 31 25 26 27 28 29 30 31 29 30
October November December
Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa
1 2 3 4 5 1 2 1 2 3 4 5 6 7
6 7 8 9 10 11 12 3 4 5 6 7 8 9 8 9 10 11 12 13 14
13 14 15 16 17 18 19 10 11 12 13 14 15 16 15 16 17 18 19 20 21
20 21 22 23 24 25 26 17 18 19 20 21 22 23 22 23 24 25 26 27 28
27 28 29 30 31 24 25 26 27 28 29 30 29 30 31
If you pass cal a single integer parameter it will print out a calendar for that year.
$ cal 2015
2015
January February March
Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa
1 2 3 1 2 3 4 5 6 7 1 2 3 4 5 6 7
4 5 6 7 8 9 10 8 9 10 11 12 13 14 8 9 10 11 12 13 14
11 12 13 14 15 16 17 15 16 17 18 19 20 21 15 16 17 18 19 20 21
18 19 20 21 22 23 24 22 23 24 25 26 27 28 22 23 24 25 26 27 28
25 26 27 28 29 30 31 29 30 31
April May June
Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa
1 2 3 4 1 2 1 2 3 4 5 6
5 6 7 8 9 10 11 3 4 5 6 7 8 9 7 8 9 10 11 12 13
12 13 14 15 16 17 18 10 11 12 13 14 15 16 14 15 16 17 18 19 20
19 20 21 22 23 24 25 17 18 19 20 21 22 23 21 22 23 24 25 26 27
26 27 28 29 30 24 25 26 27 28 29 30 28 29 30
31
July August September
Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa
1 2 3 4 1 1 2 3 4 5
5 6 7 8 9 10 11 2 3 4 5 6 7 8 6 7 8 9 10 11 12
12 13 14 15 16 17 18 9 10 11 12 13 14 15 13 14 15 16 17 18 19
19 20 21 22 23 24 25 16 17 18 19 20 21 22 20 21 22 23 24 25 26
26 27 28 29 30 31 23 24 25 26 27 28 29 27 28 29 30
30 31
October November December
Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa Su Mo Tu We Th Fr Sa
1 2 3 1 2 3 4 5 6 7 1 2 3 4 5
4 5 6 7 8 9 10 8 9 10 11 12 13 14 6 7 8 9 10 11 12
11 12 13 14 15 16 17 15 16 17 18 19 20 21 13 14 15 16 17 18 19
18 19 20 21 22 23 24 22 23 24 25 26 27 28 20 21 22 23 24 25 26
25 26 27 28 29 30 31 29 30 27 28 29 30 31
Listing 9.3 shows a calendar for the year 2015.
When passed two integer parameters, cal will interpret that as month year and will generate a calendar accordingly.
$ cal 8 2016
August 2016
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 31
Listing 9.4 shows the calendar for August, 20161.
The cat command is short for concatenate, and it does just that. It will allow us to concatenate multiple files together, but it also has a few extra tricks up its sleeve.
Without any extra flags, cat will print out the contents of a file to the standard output, usually your terminal window.
$ cat file1.txt
Lorem ipsum dolor sit amet, consectetur adipiscing elit. In ut felis sit amet
mi malesuada convallis. In eget rutrum lacus. Donec consequat, orci sit amet
porttitor hendrerit, risus mauris placerat erat, eget vestibulum diam dolor eu
erat. Donec a neque sit amet eros porta volutpat. Vestibulum lectus magna,
ultrices at rutrum euismod, scelerisque ac urna. Suspendisse augue ipsum,
condimentum at fringilla ut, dapibus eu nisi. Nam pellentesque ante convallis,
sagittis nunc a, vehicula turpis. Sed quis velit pulvinar, convallis magna in,
viverra sapien.
Listing 9.5 shows the contents of the file1.txt file.
If we supply multiple files to the cat command it will combine them all together into a single output - in this case, to the standard output.
$ cat file1.txt file2.txt
Lorem ipsum dolor sit amet, consectetur adipiscing elit. In ut felis sit amet
mi malesuada convallis. In eget rutrum lacus. Donec consequat, orci sit amet
porttitor hendrerit, risus mauris placerat erat, eget vestibulum diam dolor eu
erat. Donec a neque sit amet eros porta volutpat. Vestibulum lectus magna,
ultrices at rutrum euismod, scelerisque ac urna. Suspendisse augue ipsum,
condimentum at fringilla ut, dapibus eu nisi. Nam pellentesque ante convallis,
sagittis nunc a, vehicula turpis. Sed quis velit pulvinar, convallis magna in,
viverra sapien.
Integer suscipit augue a tempor pellentesque. Proin tincidunt magna in luctus
vulputate. Duis euismod elit sit amet pellentesque hendrerit. Suspendisse blandit
euismod mauris eu congue. Ut condimentum et est sed lobortis. Etiam vel neque
faucibus turpis accumsan imperdiet. Nullam nisl felis, pharetra quis orci vitae,
sagittis gravida augue. Interdum et malesuada fames ac ante ipsum primis in
faucibus. Maecenas vulputate tempus adipiscing. Cras aliquet nibh a ligula
varius, a varius massa tempus. Etiam porttitor neque sit amet ante laoreet, vitae
euismod ipsum ullamcorper. Nullam placerat sed est in tincidunt.
Listing 9.6 shows the two files joined together into one file and printed to the standard output (terminal window).
In the previous examples, the output of the cat command went to standard output, but we can also use the redirect operator, >, to send the output to a file.
Here is an example of how we can use the cat command to combine 2 files into a new file by using the > operator and giving it the name of the file we want to create.
$ cat file1.txt file2.txt > new_file.txt
We can then use the cat command to view the contents of the new file.
$ cat new_file.txt
Lorem ipsum dolor sit amet, consectetur adipiscing elit. In ut felis sit amet
mi malesuada convallis. In eget rutrum lacus. Donec consequat, orci sit amet
porttitor hendrerit, risus mauris placerat erat, eget vestibulum diam dolor eu
erat. Donec a neque sit amet eros porta volutpat. Vestibulum lectus magna,
ultrices at rutrum euismod, scelerisque ac urna. Suspendisse augue ipsum,
condimentum at fringilla ut, dapibus eu nisi. Nam pellentesque ante convallis,
sagittis nunc a, vehicula turpis. Sed quis velit pulvinar, convallis magna in,
viverra sapien.
Integer suscipit augue a tempor pellentesque. Proin tincidunt magna in luctus
vulputate. Duis euismod elit sit amet pellentesque hendrerit. Suspendisse blandit
euismod mauris eu congue. Ut condimentum et est sed lobortis. Etiam vel neque
faucibus turpis accumsan imperdiet. Nullam nisl felis, pharetra quis orci vitae,
sagittis gravida augue. Interdum et malesuada fames ac ante ipsum primis in
faucibus. Maecenas vulputate tempus adipiscing. Cras aliquet nibh a ligula
varius, a varius massa tempus. Etiam porttitor neque sit amet ante laoreet, vitae
euismod ipsum ullamcorper. Nullam placerat sed est in tincidunt.
Listing 9.7 shows the newly created, new_file.txt, that is the combination of both file1.txt and file2.txt.
The -b flag will print out line numbers.
$ cat -b big_file.txt
1 Lorem ipsum dolor sit amet, consectetur adipiscing elit. In ut
felis sit amet mi malesuada convallis. In eget rutrum lacus. Donec consequat,
orci sit amet porttitor hendrerit, risus mauris placerat erat, eget vestibulum
diam dolor eu erat. Donec a neque sit amet eros porta volutpat. Vestibulum
lectus magna, ultrices at rutrum euismod, scelerisque ac urna. Suspendisse
augue ipsum, condimentum at fringilla ut, dapibus eu nisi. Nam pellentesque
ante convallis, sagittis nunc a, vehicula turpis. Sed quis velit pulvinar,
convallis magna in, viverra sapien.
2 Integer suscipit augue a tempor pellentesque. Proin tincidunt magna
in luctus vulputate. Duis euismod elit sit amet pellentesque hendrerit.
Suspendisse blandit euismod mauris eu congue. Ut condimentum et est sed
lobortis. Etiam vel neque faucibus turpis accumsan imperdiet. Nullam nisl
felis, pharetra quis orci vitae, sagittis gravida augue. Interdum et
malesuada fames ac ante ipsum primis in faucibus. Maecenas vulputate tempus
adipiscing. Cras aliquet nibh a ligula varius, a varius massa tempus. Etiam
porttitor neque sit amet ante laoreet, vitae euismod ipsum ullamcorper.
Nullam placerat sed est in tincidunt.
3 Nunc vel massa vel nibh auctor aliquam. Fusce non interdum purus.
Proin at vestibulum nisl. Mauris venenatis rutrum cursus. Nunc quis rutrum
nulla. Praesent ac faucibus ligula. Donec non velit quis risus aliquet
sollicitudin. Fusce sed vestibulum est.
4 Sed feugiat lorem eu porta sodales. Ut egestas urna orci, eget
fringilla lectus malesuada ac. Etiam malesuada nulla et luctus ullamcorper.
Fusce et enim nulla. Vivamus pharetra eros non convallis fermentum. Nulla
viverra nunc nec faucibus tempor. Duis nibh ligula, tincidunt non
ullamcorper eget, iaculis vel mi. Duis tristique imperdiet venenatis.
Praesent dictum sit amet elit sit amet aliquam. Proin convallis eros sed
tortor sodales elementum. Lorem ipsum dolor sit amet, consectetur
adipiscing elit.
5 Sed eu dignissim augue. In accumsan enim diam, eu convallis nisl
pellentesque a. Pellentesque sed lorem dui. Praesent mattis ut nulla at
condimentum. Nam ut nisi porttitor, feugiat libero interdum, sollicitudin eros.
Maecenas at metus vehicula, ornare diam vitae, iaculis arcu. Duis eu mi eu
ipsum blandit viverra in nec quam. Nulla auctor, velit vel ornare congue,
libero mi porttitor mauris, nec porta orci lorem lacinia eros. Sed tristique
aliquet congue. Interdum et malesuada fames ac ante ipsum primis in faucibus.
The kill command is, unfortunately, poorly named. Its name would imply that its sole purpose is that of mischief, when in reality its purpose is to simply send messages to processes. A few of these signals will forcefully terminate a process. Others will simply tell the process to shutdown when it is ready.
Table 9.2 shows a list of the different signals (and their meaning) that can be sent to a process from the kill command.
| Signal | Value | Action | Comment |
| SIGHUP | 1 | Term | Hangup detected on controlling terminal or death of controlling process |
| SIGINT | 2 | Term | Interrupt from keyboard |
| SIGQUIT | 3 | Core | Quit from keyboard |
| SIGILL | 4 | Core | Illegal Instruction |
| SIGABRT | 6 | Core | Abort signal from abort(3) |
| SIGFPE | 8 | Core | Floating point exception |
| SIGKILL | 9 | Term | Kill signal |
| SIGSEGV | 11 | Core | Invalid memory reference |
| SIGPIPE | 13 | Term | Broken pipe: write to pipe with no readers |
| SIGALRM | 14 | Term | Timer signal from alarm(2) |
| SIGTERM | 15 | Term | Termination signal |
| SIGUSR1 | 30,10,16 | Term | User-defined signal 1 |
| SIGUSR2 | 31,12,17 | Term | User-defined signal 2 |
| SIGCHLD | 20,17,18 | Ign | Child stopped or terminated |
| SIGCONT | 19,18,25 | Cont | Continue if stopped |
| SIGSTOP | 17,19,23 | Stop | Stop process |
| SIGTSTP | 18,20,24 | Stop | Stop typed at tty |
| SIGTTIN | 21,21,26 | Stop | tty input for background process |
| SIGTTOU | 22,22,27 | Stop | tty output for background process |
Using ps that we learned about in Chapter 6 we can find the PID, or process ID, of the process that we need to stop.
The default signal for kill is 15, or SIGTERM.
$ kill 123456
In Listing 9.9 we are sending a signal to process with a PID of 123456 to peacefully shutdown when it is ready.
One of the most common use cases for kill is to forcibly terminate a process. There are two ways to do this, both ways are aliases of each other.
$ kill -9 123456
$ kill -s SIGKILL 123456
In Listing 9.10 we pass in the value of the signal we want to send to the process, -9.
In Listing 9.11 we use the -s flag and give it the name of the signal we want to send, SIGKILL.
Both Listing 9.10 and Listing 9.11 send the same information, and have the result, on the specified process.
The goal of this book is to help you master the Unix and Linux commands that will provide you with the most value on a daily basis.
We’ve covered a key subset of flags and options that will be most useful in your day-to-day work as a software developer. In some circumstances you’ll need to go beyond the scope of this book for more information.
Your first resource to find out more information about a particular command should be the man command. The man command will print out the manual for the command that you specify, including information on all flags and options.
$ man mkdir
MKDIR(1) BSD General Commands Manual MKDIR(1)
NAME
mkdir -- make directories
SYNOPSIS
mkdir [-pv] [-m mode] directory_name ...
DESCRIPTION
The mkdir utility creates the directories named as operands, in the order
specified, using mode rwxrwxrwx (0777) as modified by the current umask(2).
The options are as follows:
-m mode
Set the file permission bits of the final created directory to the
specified mode. The mode argument can be in any of the formats
specified to the chmod(1) command. If a symbolic mode is specified,
the operation characters ``+'' and ``-'' are interpreted relative to an
initial mode of ``a=rwx''.
-p Create intermediate directories as required. If this option is
not specified, the full path prefix of each operand must already exist.
On the other hand, with this option specified, no error will be
reported if a directory given as an operand already exists.
Intermediate directories are created with permission bits of
rwxrwxrwx (0777) as modified by the current umask, plus write and
search permission for the owner.
-v Be verbose when creating directories, listing them as they are
created.
The user must have write permission in the parent directory.
DIAGNOSTICS
The mkdir utility exits 0 on success, and >0 if an error occurs.
SEE ALSO
rmdir(1)
COMPATIBILITY
The -v option is non-standard and its use in scripts is not recommended.
STANDARDS
The mkdir utility is expected to be IEEE Std 1003.2 (``POSIX.2'')
compatible.
HISTORY
A mkdir command appeared in Version 1 AT&T UNIX.
BSD January 25, 1994 BSD
In Listing 9.12 we see the manual for the mkdir command.
The man command does a lot more than just display manual information. For example, it helps you to generate man pages, but that’s unlikely something you’re going to use that often.
For more information on man you can use the very “meta” command found in Listing 9.13.
$ man man
The pbcopy command is only available on OS X systems. On systems other than OS X, this functionality can be recreated using an X11 tool called xsel, which is available on most Linux systems.
So what does pbcopy do? It will read input from the standard output and copy that data into the system’s paste buffer, to be used in other places.
We can use the cat command from Section 9.2 to read in a file and then use the pipe operator, |, to send the result to pbcopy.
$ cat file1.txt | pbcopy
Lorem ipsum dolor sit amet, consectetur adipiscing elit. In ut felis sit amet
mi malesuada convallis. In eget rutrum lacus. Donec consequat, orci sit amet
porttitor hendrerit, risus mauris placerat erat, eget vestibulum diam dolor eu
erat. Donec a neque sit amet eros porta volutpat. Vestibulum lectus magna,
ultrices at rutrum euismod, scelerisque ac urna. Suspendisse augue ipsum,
condimentum at fringilla ut, dapibus eu nisi. Nam pellentesque ante convallis,
sagittis nunc a, vehicula turpis. Sed quis velit pulvinar, convallis magna in,
viverra sapien.
Listing 9.14 shows the data in the paste buffer ready to be pasted into what application you need it for.
In Section 9.5 we learned how to use the pbcopy command to copy data into the system’s paste buffer. It would make sense that if you could get data into the system’s paste buffer, there would be an easy way to get that data back out again.
The pbpaste command lets you take data from the system’s paste buffer and write it to standard out.
Let’s copy a file into the paste buffer using the pbcopy command. We’ll use the example file from the sed chapter, Chapter 7.
$ pbcopy < birthday.txt
With data in the paste buffer we can use the pbpaste command to pipe that data into another command.
$ pbpaste | ag name
Happy Birthday Dear (name)
In Listing 9.15 we took the data from the system’s paste buffer and piped it into the ag command (Chapter 2) to search for the word “name”.
The tail command allows us to look at the end of a file, and even more so will let us watch a file as it is being written to, making it perfect for monitoring log files in a production environment.
n Lines of a FileBy default, when you pass a file name to the tail command the last ten lines of the file will be printed to the screen, and tail will exit. Listing 9.16 shows the last ten lines of the /var/log/system.log file.
$ tail /var/log/system.log
Dec 5 15:46:22 markmini.home Google Chrome Helper[62354]: Process unable to ...
Dec 5 15:46:22 markmini.home Google Chrome Helper[62354]: Process unable to ...
Dec 5 15:46:22 markmini.home Google Chrome Helper[62354]: CGSLookupServerRoo...
Dec 5 15:46:24 markmini.home Google Chrome Helper[62357]: Internals of CFAll...
Dec 5 15:46:24 markmini.home Google Chrome Helper[62357]: Process unable to ...
Dec 5 15:46:24 markmini.home Google Chrome Helper[62357]: Process unable to ...
Dec 5 15:46:24 markmini.home Google Chrome Helper[62357]: CGSLookupServerRoo...
Dec 5 15:49:19 markmini.home mds[100]: (Warning) Volume: vsd:0x7fcd9c5a0800 ...
DisabledRecycleCount = 8;
}
If we want to change the number of lines that are displayed by tail we can use the -n flag.
$ tail -n 5 /var/log/system.log
Dec 5 15:46:24 markmini.home Google Chrome Helper[62357]: Process unable to ...
Dec 5 15:46:24 markmini.home Google Chrome Helper[62357]: CGSLookupServerRoo...
Dec 5 15:49:19 markmini.home mds[100]: (Warning) Volume: vsd:0x7fcd9c5a0800 ...
DisabledRecycleCount = 8;
}
Listing 9.17 shows the last five lines in the /var/log/system.log file.
Using the -r flag we can reverse the direction of how tail displays the selected lines of the file to us. By default, the last line of the output is the last line of the file, but the -r flag will reverse that to make the last line of the file the first line of the output.
$ tail -r -n 5 /var/log/system.log
}
DisabledRecycleCount = 8;
Dec 5 15:49:19 markmini.home mds[100]: (Warning) Volume: vsd:0x7fcd9c5a0800 ...
Dec 5 15:46:24 markmini.home Google Chrome Helper[62357]: CGSLookupServerRoo...
Dec 5 15:46:24 markmini.home Google Chrome Helper[62357]: Process unable to ...
Listing 9.18 shows the last five lines of a file with the newest line at the top of the output, and the oldest line at the bottom of the output.
Quite possibly one of the most used commands and flags in any production environment is the tail command with the -f flag. When using the -f flag, tail will never exit and will continue to output new data as it is added to the end of the watched file.
$ tail -f /var/log/system.log
As new lines are being written to /var/log/system.log they will automatically be displayed, without the need to refresh or run the command again.
When watching a “live” file, often referred to as “tailing” a file, we may want to filter the output so we can find exactly the lines of data that are the most important to us. An example of this would be wanting only to see lines from a web server log file that come from a certain IP address.
We can easily use the pipe operator, |, to send the live stream of data from tail to a command (such as ag that we learned about in Chapter 2) to filter the data easily for us.
$ tail -f /var/log/system.log | ag com.apple.windowserver
Dec 5 15:46:22 markmini.home Google Chrome Helper[62354]:
CGSLookupServerRootPort: Failed to look up the port for
"com.apple.windowserver.active" (1100)
Dec 5 15:46:24 markmini.home Google Chrome Helper[62357]:
CGSLookupServerRootPort: Failed to look up the port for
"com.apple.windowserver.active" (1100)
When combining tail -f with ag we can watch as the exact data we want from a “live” file is continuously printed to our screen without needing to continually refresh. This combination is a must for production (and even development) environments.
Using the tree command, you can recursively list the contents of a directory in a tree-like format. This is handy when you want to get a high-level view of all the directories and files inside of a project for example.
By default, tree will list all of the directories and files in a given directory, but it also comes with many flags that will alter the level of detail you get back.
tree may or may not be installed by default on your machine. If tree is not installed then you should visit the tree homepage for instructions on how to install it on your system.
If you are on a Mac, the best and easiest way to install tree is using Homebrew.
$ brew install tree
If you are on a different platform, please see the install directions on the project’s page for the correct installation instructions for your platform.
By default when you use the tree command, it will output a list of all of the files and directories in the current directory, recursively.
$ tree
.
├── assets
│ ├── images
│ │ └── image.jpg
│ ├── javascripts
│ │ ├── application.js
│ │ └── curly.js.coffee
│ └── stylesheets
│ ├── application.css
│ └── curly.css.scss
├── controllers
│ ├── application_controller.rb
│ ├── concerns
│ └── curly_controller.rb
├── helpers
│ ├── application_helper.rb
│ └── curly_helper.rb
├── mailers
├── models
│ └── concerns
└── views
├── curly
│ └── echo.html.erb
└── layouts
└── application.html.erb
In Listing 9.20 we can see a recursive list of all files and directories in the current directory.
-L)The tree command will let us limit the depth of its recursion if we want using the -L flag and giving it a number of levels we want the recursion to go. This can be helpful in very deep directories, where you only want an overview of what’s under the surface.
$ tree -L 2
.
├── assets
│ ├── images
│ ├── javascripts
│ └── stylesheets
├── controllers
│ ├── application_controller.rb
│ ├── concerns
│ └── curly_controller.rb
├── helpers
│ ├── application_helper.rb
│ └── curly_helper.rb
├── mailers
├── models
│ └── concerns
└── views
├── curly
└── layouts
In Listing 9.21 we told tree to only recurse down two levels; files and directories that are deeper, such as those under the views/curly directory, are not listed.
-d)By default tree will list both files and directories. Often it is useful just to see a list of directories without the files cluttering up the tree. We can use the -d flag to print out just the directories.
$ tree -d
.
├── assets
│ ├── images
│ ├── javascripts
│ └── stylesheets
├── controllers
│ └── concerns
├── helpers
├── mailers
├── models
│ └── concerns
└── views
├── curly
└── layouts
Using the -d flag in Listing 9.22 we see only a list of directories under the current directory.
So far we have been using tree to print out a listing of the current directory, but like the ls command (Chapter 1 Section 1.3), we can also give it a path to another directory.
$ tree -d /usr/local/etc/
/usr/local/etc/
├── ImageMagick
├── bash_completion.d
│ └── helpers
├── fonts
│ └── conf.d
├── openssl
│ └── misc
├── profile.d
└── rabbitmq
As we can see in Listing 9.23 we have printed out a tree listing of all of the directories under my /usr/local/etc/ directory.
The wc command provides two really useful functions, it will both count the number of words in a file, as well as the number of lines in a file.
-w)If we want to count the number of words in a file we can use the -w flag.
$ wc -w /usr/share/dict/web2a
121847 /usr/share/dict/web2a
As we can see in Listing 9.24 the /usr/share/dict/web2a file contains 121847 words.
-l)To count the number of lines in a file we can use the -l flag.
$ wc -l /usr/share/dict/web2a
76205 /usr/share/dict/web2a
Listing 9.25 shows that our file contains 76205 lines in it.
As we’ve seen throughout the examples in this book, we, as developers, often need to chain Unix commands together to accomplish certain tasks. We can use the pipe operator, |, to supply the input to the WC command to count the number of occurrences of a word or line in the input.
In the section on Ag/Ack 2.2, we saw how we could search for the occurrences of “DHH” in the Rails source code. But what if we just wanted to count the occurrences of the phrase “DHH” in the code? Simple, we can accomplish that by piping the ag output into wc with the pipe operator, |.
$ ag DHH | wc -l
The result of our search should look something like Listing 9.26:
26