The {pnk}f(eli)x Blog

The informal ramblings of an ex-pat PL enthusiast

Better Command Completion in Bash on OS X

(This post started as a personal e-mail to Niko, and then I figured it was blog worthy.)

There’s plenty of problems when working atop “OS X”; but no need to be jealous of Shu’s zsh setup (at least not for its tab-completion on git stuff), at least not if you are already using Homebrew. Just install brew’s bash completion package!

Executive summary:

% brew install bash-completion

% echo >> ~/.bash_profile <<END
  if [ -f $(brew --prefix)/etc/bash_completion ]; then
    . $(brew --prefix)/etc/bash_completion

And voilĂ !

See also potentially related topics from super user, stack overflow, milkbox blog.

Note also that I did burn myself by trying to get too smart: In particular, after reading stack overflow, I over-eagerly attempted to address a purported problem by installing the homebrew newer git instead of the default (older) built-in git installed by Apple.

This was a little more painful than I expected, because there were a bunch of git-related commands already in my /usr/local/bin, probably I had likely already copied git to there once before by hand, and so brew kept aborting the installation because it did not want to overwrite the binaries that it was not already managing. I think brew was aborting the install in a sound transactional manner, but I am not 100% sure of that, because at least one point the command completion stopped working and at that point I just

  1. gave up on understanding where everything came from,
  2. moved the non-brew git-related material in /usr/local/bin/ out of the way, and
  3. redid the brew install git

Anyway, I should also give a shout-out to Axel Hecht; his post on Mozilla’s Yammer instance is what got me to the point of even attempting to install this piece of marvelousness.

(Also, further posts on yammer are lightly pushing for readers to consider zsh as an alternative to bash. I do not think I am ready to switch to zsh, but I can at least link to the blog post arguing for zsh.)

Update (written 2013 april 16): Now that I have decent command/context sensitive completion in bash in my terminal, of course I want to have it in my Emacs M-x shell as well. At first I was dismayed that I did not just get that “out of the box”; then I was happy after some googling to discover: bash-completion.el, which forwards the completion requests onto a separate bash process, so that one inherits the same completions that bash provides in the terminal, with no Emacs hacking.

Well, at least, not very much Emacs hacking.

It turns out that I had to do a little bit of Emacs hacking in order to get the setup working, at least for my idiosyncratic bash setup. In particular, it seems like the Elisp code for bash-complete.el assumes that one is setting one’s prompt via the PS1 environment variable, while mine is often set via the PROMPT_COMMAND environment variable. After determining what is going on, it is easy enough to fix this (and the corresponding solution has even been filed as a pull request in the github repo).