commit ee0d42a4860aec53c999fcd18c1ec1262b107f34
parent cde467ab49e50f1811d7b6c828c3aeedcd0cad41
Author: spacehobo <spacehobo@web>
Date: Sun, 17 May 2026 18:17:57 +0200
Link to stagit instead of inlining the code.
Diffstat:
| M | spacehobo.mdwn | | | 82 | ++++++++++++++++++++++--------------------------------------------------------- |
1 file changed, 23 insertions(+), 59 deletions(-)
diff --git a/spacehobo.mdwn b/spacehobo.mdwn
@@ -1,67 +1,16 @@
-# Just a Rum-Soaked Space Hobo with a Heart full of Love
+# Just a Rum-Soaked Space Hobo with an Inordinate Fondness for Makefiles
-Hey, check out my neat `bash` prompt, which I put in eik's `/etc/bash_completion.d/prompt.bash` so everyone gets it:
+## Prompt Engineering
-```{sh}
-# Detect if we're in via ssh, sudo, or doas, or our session type is "tty"
-unset _tty
-_tty=$SSH_CONNECTION$SUDO_USER$DOAS_USER
-[ "$XDG_SESSION_TYPE" = "tty" ] && _tty="yes"
-
-GIT_PS1_SHOWDIRTYSTATE='y'
-GIT_PS1_SHOWSTASHSTATE='y'
-GIT_PS1_SHOWUNTRACKEDFILES='y'
-GIT_PS1_DESCRIBE_STYLE='contains'
-GIT_PS1_SHOWUPSTREAM='auto'
-# We use defined/undef logic on array indices to control values inside the
-# prompt, which is faster than shelling out to test data
-_noop[0]='array accesses turn 0/nonzero into defined/undef!'
-
-case "$TERM" in *itty*|foot*|*color*) color_prompt=yes;; esac
-
-if [ "$color_prompt" = yes ]; then
- GIT_PS1_SHOWCOLORHINTS='y'
-else
- # simpler, uncoloured version
- unset GIT_PS1_SHOWCOLORHINTS
- PS1='\$ '
- type -t __git_ps1 > /dev/null && PS1='$(__git_ps1 "{%s}")'$PS1
- PS1='${SSH_CONNECTION:+\h:}\w'$PS1
- PS1='${_tty:+\u${DOAS_USER:+<$DOAS_USER>}${SUDO_USER:+<$SUDO_USER>}@}'$PS1
- PS1='${debian_chroot:+($debian_chroot)}'$PS1
- PS1='${_noop[$(($?==0))]:+($?)}${_noop[$((\j==0))]:+[\j]}'$PS1
- return
-fi
+Hey, check out my neat `bash` prompt, which I put in eik's `/etc/bash_completion.d/prompt.sh` so everyone gets it:
-# We build the shell from right to left, starting with a
-# $ or # that is either bold default, or blinking red
-# if $? is nonzero
-PS1='\[\e[$(($?==0?0:91));$(($?==0?1:5))m\]\$\[\e[0m\] '
-# Git branch information between gold curly braces
-type -t __git_ps1 > /dev/null && PS1='$(__git_ps1 "\[\e[1;33m\]{%s\[\e[1;33m\]}")'$PS1
-# The only straightforward part: current directory in blue
-PS1='\[\e[1;34m\]\w'$PS1
-# If we ssh'd here, show the hostname in green
-PS1='${SSH_CONNECTION:+\[\e[1;32m\]\h\[\e[1;33m\]:}'$PS1
-# If this is our local machine and we didn't sudo, we should know
-# our username already! Otherwise if it's "tty", show it in purple.
-# If we did sudo/doas, show the username we came from in red.
-PS1='${_tty:+\[\e[1;35m\]\u\[\e[1;91m\]${SUDO_USER:+<$SUDO_USER>}${DOAS_USER:+<$DOAS_USER>}\[\e[1;33m\]@}'$PS1
-# If the debian_chroot var is defined, show it in cyan.
-PS1='${debian_chroot:+\[\e[1;36m\]($debian_chroot)}'$PS1
-# If the number of jobs suspended/backgrounded is nonzero,
-# show it in yellow square brackets.
-PS1='${_noop[$((\j==0))]:+\[\e[1;33m\][\j]}'$PS1
-# Likewise if the last exit code was non-zero,
-# show it in red parentheses.
-PS1='${_noop[$(($?==0))]:+\[\e[1;91m\]($?)}'$PS1
-```
+ * [Prompt Engineering](https://git.permacomputing.net/prompt-engineering/files.html)
The prompt environment is fairly limited. It can do parameter expansion, reference expansion, arithmetic expansion, and a couple other neat tricks. You can shell out, but if you do that overwrites the variable that contains the exit code of the last program you ran (`$?`). Tools such as the `__git_ps1` hacks do their best to only use features of bash that work internally to bash itself.
This prompt uses the `_noop` array (with only `${_noop[0]}` defined) to turn arithmetic expressions into defined/undefined responses. This lets us use some of the brace-expansion features to specify alternate output, so we can display the error code or number of jobs in the background *only* if they're non-zero, and we can style them with a high degree of freedom.
-It also only displays the hostname if the `$XDG_SESSION_TYPE` is `"tty"` or if we have variables set by `ssh`, `sudo`, or `doas`. It dynamically displays the `$SUDO_USER` and `$DOAS_USER`, if that is available.
+It also only displays the hostname if the `$XDG_SESSION_TYPE` is `"tty"` or if we have variables set by `ssh`, `sudo`, or `doas`. It dynamically displays the `$SUDO_USER` and `$DOAS_USER`, if either is defined.
What this means is that on your local desktop system, when you log in, your prompt is merely:
@@ -71,10 +20,25 @@ But the same prompt on a remote system will show the more common:
user@hostname:~$
-And if you are in a chroot with background processes looking at a git repo after a command that exited with an error code of `1`:
+And if you are sudo'd in a chroot with background processes looking at a git repo after a command that exited with an error code of `1`:
+
+ (1)[2](thechroot)root<user>@hostname:~/src/therepo{main $%}#
- (1)[2](thechroot)user@hostname:~/src/therepo{main $%}$
+with coloured styling information on all the various parts, if `tput setaf 1` was successful on your terminal or your `$TERM` seems likely to support it. Otherwise you get a plain text version. Here's the plain text version so you can see how it works:
-with coloured styling information on all the various parts, if `tput setaf 1` was successful on your terminal. Otherwise you get a plain text version.
+```sh
+unset _tty
+_tty=$SSH_CONNECTION$SUDO_USER$DOAS_USER
+[ "$XDG_SESSION_TYPE" = "tty" ] && _tty="yes"
+# We use defined/undef logic on array indices to detect non-zero values inside
+# the prompt, which is faster than shelling out
+_noop[0]='array accesses turn 0/nonzero into defined/undef!'
+ PS1='${_noop[$(($?==0))]:+($?)}${_noop[$((\j==0))]:+[\j]}'
+ PS1+='${debian_chroot:+($debian_chroot)}'
+ PS1+='${_tty:+\u${DOAS_USER:+<$DOAS_USER>}${SUDO_USER:+<$SUDO_USER>}@}'
+ PS1+='${SSH_CONNECTION:+\h:}\w'
+ type -t __git_ps1 > /dev/null && PS1+='$(__git_ps1 "{%s}")'
+ PS1+='\$ '
+```
I just think it's neat!