Though I’ve written several shell-related posts, I’m not a shell geek. Let’s get that out of the way right now. The shell is a tool for me and nothing more. I had used tcsh for years and years and years for no other reason than someone told me it was better than bash when I first started doing any “real” Unix work. I recently moved to bash because, frankly, I was tired of having to custom-configure every system I login to on a regular basis. Bash is the default shell for most Unix flavors and since the shell is only a tool, I saw no reason to continue spending time on customizations.
The other day when @patrick_mc dropped a link to a bash mastery article in a tweet, I saw the opportunity to learn something. Though it was hardly a masterful type article, I did learn about one thing that I didn’t know about before: CDPATH.
The details of CDPATH are outside of the scope of this post, but the gist is that it works the way that the PATH works. Type a directory and if it’s in your CDPATH, the OS will find it and change to that directory by name alone – even if the directory name isn’t in your current working directory. For example, if I’m in my home directory, I can type www and be delivered directly to /Users/me/Development/www as long as /Users/me/Development is in my CDPATH.
When I first read the article, I was at work and on my Ubuntu machine so I tried it there first by adding the following line to my /home/me/.bash_profile:
After sourcing ($ source .profile) my updated profile, I was able to jump to directories exactly as advertised. Moreover, tab completion worked brilliantly so, from my home directory, I could type cd w[TAB] and it would complete to cd www. Brilliant.
It wasn’t quite so easy on the Mac, though. I updated my .profile, but couldn’t get it to work. I thought I had a syntax error in my .profile, but after hours of trial and error, I was no closer. I pinged the #lazyweb on Twitter to ask whether it worked for others on OS X and got more than a few affirmative responses which just confused me even more. A quick chat with Brad Greenlee, though, pointed out the error of my ways. It turned out that CDPATH was working great, but I was assuming (yeah, I know) that tab completion would also work. It didn’t.
For me, something like CDPATH is only useful with tab completion because otherwise, I can tab complete the full path to the file before I can type the entire directory name (for all but the shortest directory names). Besides, the Tab key is completely woven into the fabric of my muscle memory now. I can’t give it up when I’m in the shell. After a little digging, I found the answer:
$ sudo port install bash-completion
Yep, that’s it (assuming you have MacPorts installed). Well, almost. You do have to update your .profile (or .bash_profile, .bashrc, etc.) to source the installed file at /opt/local/etc/bash_completion. Instructions for doing so are printed in the output of the installation. In case you close your window too early, though:
if [ -f /opt/local/etc/bash_completion ]; then . /opt/local/etc/bash_completion fi