Eu reescrevi isso recentemente, baseado em outro script que eu escrevi anos atrás - este é otimizado para rodar dentro do bash o máximo possível, para evitar garfos caros. Foi quase 8x mais rápido que minha função antiga que usava o awk / sed.
Produz bons resultados. Ele mantém a parte pwd do prompt em no máximo MAX_PWD_LENGTH caracteres e, se você estiver em um subdiretório de $ HOME, isso também ficará claro:
Exemplos:
pc770-ubu:~ $ cd ~/a/b/c
pc770-ubu:~/a/b/c $ cd d/e/f
pc770-ubu:~/a/b/c/d/e/f $ cd g
pc770-ubu:~/a/b/c/d/e/f/g $ cd h
pc770-ubu:~/a/b/c/d/e/f/g/h $ cd i
pc770-ubu:~/a/b/c/d/e/f/g/h/i $ cd j
pc770-ubu:~/a/b/c/d/e/f/g/h/i/j $ cd k
pc770-ubu:~/a/b/c/d/e/f/g/h/i/j/k $ cd l
pc770-ubu:~../c/d/e/f/g/h/i/j/k/l $ cd m
pc770-ubu:~../d/e/f/g/h/i/j/k/l/m $ cd n
pc770-ubu:~../e/f/g/h/i/j/k/l/m/n $ cd o
pc770-ubu:~../f/g/h/i/j/k/l/m/n/o $ cd /tmp/a/b/c/d/e/f
pc770-ubu:/tmp/a/b/c/d/e/f $ cd g
pc770-ubu:/tmp/a/b/c/d/e/f/g $ cd h
pc770-ubu:/tmp/a/b/c/d/e/f/g/h $ cd i
pc770-ubu:/tmp/a/b/c/d/e/f/g/h/i $ cd j
pc770-ubu:/../a/b/c/d/e/f/g/h/i/j $ cd k
pc770-ubu:/../b/c/d/e/f/g/h/i/j/k $ cd l
pc770-ubu:/../c/d/e/f/g/h/i/j/k/l $ cd m
pc770-ubu:/../d/e/f/g/h/i/j/k/l/m $ cd
pc770-ubu:~ $
A função bash (chamar isso ao construir sua variável PS1):
# set this to whatever you want:
MAX_PWD_LENGTH=20
function shorten_pwd
{
# This function ensures that the PWD string does not exceed $MAX_PWD_LENGTH characters
PWD=$(pwd)
# if truncated, replace truncated part with this string:
REPLACE="/.."
# determine part of path within HOME, or entire path if not in HOME
RESIDUAL=${PWD#$HOME}
# compare RESIDUAL with PWD to determine whether we are in HOME or not
if [ X"$RESIDUAL" != X"$PWD" ]
then
PREFIX="~"
fi
# check if residual path needs truncating to keep total length below MAX_PWD_LENGTH
# compensate for replacement string.
TRUNC_LENGTH=$(($MAX_PWD_LENGTH - ${#PREFIX} - ${#REPLACE} - 1))
NORMAL=${PREFIX}${RESIDUAL}
if [ ${#NORMAL} -ge $(($MAX_PWD_LENGTH)) ]
then
newPWD=${PREFIX}${REPLACE}${RESIDUAL:((${#RESIDUAL} - $TRUNC_LENGTH)):$TRUNC_LENGTH}
else
newPWD=${PREFIX}${RESIDUAL}
fi
# return to caller
echo $newPWD
}
EDIT: bug fixo com comprimento absoluto de string