Per-computer colored prompts in bash

I use my Athena account from many computers, often multiple computers at once via SSH, and it’s useful to keep track of which terminal is showing a prompt from which computer. One reasonably easy way to accomplish that is to color the prompt as a function of which computer I’m on. Here’s what I use in my .bashrc:

export PS1="\[\e[1;$((31 + $(hostname | cksum | cut -c1-3) % 6))m\]\h\[\e[0m\]:\w \u\$ "

From inside out:

hostname gets the name of the current computer.

cksum gives me a checksum of its input, which I’m basically just using as a well-known hash function with numerical output.

cut picks out certain characters from the input, in this case the first three digits/characters, because checksums can be fairly large.

$(...) means to evaluate a command and substitute it’s output. (If you’re familiar with backticks, it’s the same thing, except that $(... $(...)) works the way you want and `... `...`` doesn’t.)

$((...)) evaluates arithmetic. In this case, we take the checksum and get the remainder when divided by six and add it to 31, so we get a number between 31 and 36. This happens to be the range of ANSI color codes excluding white and black.

\e[1;35m (or whatever the number happens to be is the full ANSI escape sequence to turn the prompt a certain color, bolded.

\[ and \] tell bash that the intervening text in a prompt is a formatting code, and shouldn’t be counted towards the length of the prompt, although it doesn’t seem to work for me. It might be related to this snide observation about the code that displays the prompt; I’ve never looked into it in detail.

\h actually displays the hostname in the appropriate color, and \[\e[0m\] resets the colors to default.

\w prints my working directory and \u my username: I sometimes use this prompt or my .bashrc on other accounts, so it’s preferable not to hard-code it.

\$ prints a dollar sign most of the time, except that it prints a pound sign if the shell belongs to root: this is a classic UNIX way of distinguishing the superuser account. Again, I sometimes reuse my prompt, so it’s nice to have this flexibility.

Finally, I stuff the result into the PS1 variable.

So, I get something like this:

kid-icarus:~ geofft$ logout
Connection to kid closed.
dr-wily:~ geofft$

If you want more background on bash prompts in general, check out the section of the bash manual on prompts.

25 July 2010