J'ai ceci dans mon .bashrc:
LIGHTGREEN="\[\033[1;32m\]"
LIGHTRED="\[\033[1;31m\]"
WHITE="\[\033[0;37m\]"
RESET="\[\033[0;00m\]"
function error_test {
if [[ $? = "0" ]]; then
echo -e "$LIGHTGREEN"
else
echo -e "$LIGHTRED"
fi
}
PS1="\u\$(error_test)@\w$RESET \$ "
Cela semble rendre la sortie du shell exactement:
username\[\]@~/
Les échappements [et] autour des codes de couleur apparaissent dans mon invite. Si je supprime les codes d'échappement autour des couleurs, cela fonctionne, mais le retour à la ligne bash échoue incroyablement.
Notez que si PS1="LIGHTGREEN - whatever - $RESET"
cela fonctionne et que les [et] ne sont pas échappés. Cependant, je veux faire cela dans une fonction, ce qui semble être le problème.
Je ne trouve pas de bonne documentation à ce sujet. man echo
ne liste même pas une option -e. Bash semble posséder beaucoup de connaissances documentées et non documentées.
J'ai trouvé ce sujet à la recherche de réponses sur la définition de la couleur bash avec l'échappement de \[ \]
depuis la fonction bash.
En fait, il y a une solution. Bash permet de générer l'invite PS1
chaque fois que l'invite est rendue.
set_bash_Prompt(){
PS1="\u@\h $(call_your_function) $>"
}
Prompt_COMMAND=set_bash_Prompt
De cette façon, PS1 sera interprété à chaque fois que Invite sera affichée. Elle appellera donc function et restituera correctement toutes les séquences d'échappement, y compris \[ \]
, qui sont importantes pour compter la longueur de Prompt (par exemple, pour que l'historique des commandes fonctionne correctement).
J'espère que cela aidera quelqu'un, car je passe une demi-journée à résoudre ce problème.
Utilisez \001
au lieu de \[
et \002
au lieu de \]
et soyez conscient des conséquences de l’utilisation dePrompt_COMMAND
car cette méthode réinitialisera l’invite à chaque fois (ce qui peut également correspondre à vos souhaits).
La solution pour bash Prompt faisant écho aux couleurs d’une fonction est expliquée here :
Les
\[
\]
ne sont spéciaux que lorsque vous attribuez PS1. Si vous les imprimez Dans une fonction qui s'exécute lorsque l'invite est affichée, cela ne fonctionne pas . Dans ce cas, vous devez utiliser les octets\001
et\002
.
Il y a aussi cette autre réponse qui pointe dans la même direction:
\[
et\]
spécifiques à Bash sont en fait traduits en\001
et\002
Définir PS1
dans une fonction appelée par Prompt_COMMAND
comme suggéré dans l'option acceptée, réinitialise PS1
à chaque fois, ce qui empêche les autres scripts de modifier facilement votre promtp (par exemple, Python virtualnenv activate.sh ):
$ echo $PS1
<your PS1>
$ PS1="(TEST)$PS1"
$ echo $PS1
<(TEST) is not prepended to PS1 if you are using Prompt_COMMAND as it is reset>
\[
et \]
doivent être utilisés directement dans $PS*
, plutôt que de simplement les sortir via echo
.
LIGHTGREEN="\033[1;32m"
LIGHTRED="\033[1;31m"
WHITE="\033[0;37m"
RESET="\033[0;00m"
function error_test {
if [[ $? = "0" ]]; then
echo -e "$LIGHTGREEN"
else
echo -e "$LIGHTRED"
fi
}
PS1="\u\[\$(error_test)\]@\w\[$RESET\] \$ "
Voici la partie colorée du code de sortie de mon PS1
code :
color_enabled() {
local -i colors=$(tput colors 2>/dev/null)
[[ $? -eq 0 ]] && [[ $colors -gt 2 ]]
}
BOLD_FORMAT="${BOLD_FORMAT-$(color_enabled && tput bold)}"
ERROR_FORMAT="${ERROR_FORMAT-$(color_enabled && tput setaf 1)}"
RESET_FORMAT="${RESET_FORMAT-$(color_enabled && tput sgr0)}"
# Exit code
PS1='$(exit_code=$?; [[ $exit_code -eq 0 ]] || printf %s $BOLD_FORMAT $ERROR_FORMAT $exit_code $RESET_FORMAT " ")'
Capture d'écran (avec un chemin d'accès au référentiel Subversion anonymisé):
Cela fonctionnera bien.
LIGHTGREEN="\e[32m"
LIGHTRED="\e[31m"
RESET="\e[0m"
error_test () {
if [[ $? = "0" ]]; then
echo -e "$LIGHTGREEN"
else
echo -e "$LIGHTRED"
fi
}
export PS1=$(printf "$(error_test) $(whoami)@${RESET}$(pwd) ")
Je réalise que c'est un sujet ancien, mais je viens de travailler avec des fonctions. L'astuce consiste à séparer les parties imprimantes et non imprimantes de la fonction pour pouvoir fixer correctement les parties non imprimables à l'aide de []. Normalement, j'aime que ma ligne ERROR .. soit séparée (et que ce n'est pas un problème pour le moment), mais cela fonctionne également correctement si tout est sur une seule ligne.
Notez que je retourne le $ précédent? valeur de chaque sous-shell donc $? se propage de l'un à l'autre.
PS1="\n\
\[\`
cja_prv_retval=\$?;
if [ \$cja_prv_retval != 0 ];
then echo -ne \$E_ERROR;
fi
exit \$cja_prv_retval
\`\]\
\`
cja_prv_retval=\$?;
if [ \$cja_prv_retval != 0 ];
then echo -ne \"ERROR: RETURN CODE \$cja_prv_retval\";
fi
exit \$cja_prv_retval
\`\
\[\`
cja_prv_retval=\$?;
if [ \$cja_prv_retval != 0 ];
then echo -ne \$E_RESET;
fi
exit \$cja_prv_retval
\`\]\
${P_RESET}${P_GRAY}\! \t ${P_RED}\u${P_GRAY}@${P_GREEN}\h ${P_YELLOW}\w ${P_CYAN} ══>${P_RESET} "
Cela me donne non plus
2021 12:28:05 cja@morpheus04 ~ ══>
s'il n'y a pas d'erreur, ou
ERROR: RETURN CODE 1 2021 12:28:16 cja@morpheus04 ~ ══>
s'il y a une erreur. Tout est correctement espacé (l'édition d'historique multiligne fonctionne correctement).