我正在研究 bash 提示符。我还尝试智能地创建提示,以便它易于阅读和维护。这意味着没有一个巨大的export PS1
.
各种来源(包括这个问题)参考格式化的需要\[
和\]
周围的格式化,以帮助 bash 知道不要用长命令覆盖提示符。
创建PROMPT_LAST_EXIT_STATUS
字符串时,目的是用$?
红色显示最后一个命令 ( ) 的退出状态,或者不显示任何内容(如果$?
为 0)。这可行,但提示中显示了文字[
s 和s,并且长命令问题仍然存在。]
这可能是某个地方的逃避问题,但我还没有找到它。
以下代码位于~/.bashrc
.
prompt_last_exit_status () {
PROMPT_LAST_EXIT_STATUS="${?}";
if [[ ${PROMPT_LAST_EXIT_STATUS} == "0" ]];
then
PROMPT_LAST_EXIT_STATUS=
else
PROMPT_LAST_EXIT_STATUS=\[$(tput setaf 1)$(tput bold)\]${PROMPT_LAST_EXIT_STATUS}
PROMPT_LAST_EXIT_STATUS+=\[$(tput sgr0)\]
PROMPT_LAST_EXIT_STATUS+=" "
fi;
}
prompt_command () {
prompt_last_exit_status
}
export PROMPT_COMMAND=prompt_command
PS1="\${PROMPT_LAST_EXIT_STATUS}"
PS1+="\[$(tput setaf 6)$(tput bold)\]\w"
PS1+="\[$(tput sgr0)\] \$ \[$(tput sgr0)\]"
export PS1
答案1
您的分配PROMPT_LAST_EXIT_STATUS
没有被引用,因此您没有将\[
and\]
放入字符串中,您只是将[
and ]
(因为\
s 被视为转义字符)。
比较:
$ foo=\[hello\]
$ echo "$foo"
[hello]
对比:
$ foo="\[hello\]"
$ echo "$foo"
\[hello\]
不仅如此:参数扩展(将变量插入到提示字符串中)发生在提示特殊字符扩展之后。因此,将\[
and\]
放入变量中PROMPT_LAST_EXIT_STATUS
是行不通的,因为当$PROMPT_LAST_EXIT_STATUS
扩展时,\[
and\]
不再特殊。一个有效的替代方案是将颜色设置变为无条件,例如:
prompt_last_exit_status () {
PROMPT_LAST_EXIT_STATUS="${?}"
if [[ ${PROMPT_LAST_EXIT_STATUS} == "0" ]]
then
PROMPT_LAST_EXIT_STATUS=
else
PROMPT_LAST_EXIT_STATUS+=" "
fi
}
prompt_command () {
prompt_last_exit_status
}
export PROMPT_COMMAND=prompt_command
PS1="\[$(tput setaf 1)$(tput bold)\]\${PROMPT_LAST_EXIT_STATUS}\[$(tput sgr0)\]"
PS1+="\[$(tput setaf 6)$(tput bold)\]\w"
PS1+="\[$(tput sgr0)\] \$ \[$(tput sgr0)\]"
export PS1
答案2
PS1 将\[
and计算\]
为 1 和 2。如果您不想将\[
and 的颜色放入 PS1 中,因为它太长,您可以让 PS1 使用已经包含 1 和 2 的变量。如果您使用$'\001'
and 将,变量将包含 1如果使用 则包含 2 $'\002'
。我已经修改了您的代码以使其按编写的方式工作。
prompt_last_exit_status () {
PROMPT_LAST_EXIT_STATUS=$?
if [[ ${PROMPT_LAST_EXIT_STATUS} == "0" ]]; then
PROMPT_LAST_EXIT_STATUS=
else
PROMPT_LAST_EXIT_STATUS=$'\001'$(tput setaf 1)$(tput bold)$'\002'$PROMPT_LAST_EXIT_STATUS
PROMPT_LAST_EXIT_STATUS+=$'\001'$(tput sgr0)$'\002'
PROMPT_LAST_EXIT_STATUS+=" "
fi
}
prompt_command () {
prompt_last_exit_status
}
export PROMPT_COMMAND=prompt_command
PS1='$PROMPT_LAST_EXIT_STATUS'
PS1+="\[$(tput setaf 6)$(tput bold)\]\w"
PS1+="\[$(tput sgr0)\] \$ \[$(tput sgr0)\]"
export PS1
额外信息
您还可以让 PS1 引用在评估 PS1 时将调用的函数。
print_status() {
printf "\001$(tput setaf 1)$(tput bold)\002$?\001$(tput sgr0)\002"
}
export -f print_status
export PS1='$(print_status) '
注意:导出函数print_status
将确保当您 时su
,PS1 能够引用它所依赖的函数。另外,请确保任何导出的函数都可以与标准 Bourne shell (sh) 配合使用,因为 git 和 vim 使用这些 shell 并将尝试使用这些函数。