bash美化(bash配置)
前言
最近在折腾Duo S觉得上面bash一点颜色都没有,忒难看,于是开始自己动手美化bash,最终得到这篇文章的.bashrc文件,还请大家过目!
由于这不算一个项目,所以就不把老版本内容保留了。最新版代码就贴在博客,可以通过右侧导航栏快速移到那里!
效果展示-v2.8.2
附 效果展示截图 一份~ 请注意查收~
路径折叠仿照fish,父目录为单字符缩写(隐藏目录为两个字符)。耗时变为复合型,将整条命令的时间记录(即上条提示符命令被执行到这个提示符出现的时间,精确度为1ms)
代码展示-v2.8.2
重要消息
ble.sh 不建议搭配使用,建议搭配thefuck,因为ble.sh篡改已用$PROMPT_COMMAND,导致计时功能不稳定。+=()确保不被覆盖
#!/bin/bash
# ~/.bashrc
# Version : 2.8.2
# Update-time : 2025-8-17
# Author : BiaoZyx
# Email : BiaoZyx@outlook.com
# 在交互shell启用bash自动补全,建议安装`bash-completion`并启用
if ! shopt -oq posix; then
if [ -f /usr/share/bash-completion/bash_completion ]; then
. /usr/share/bash-completion/bash_completion
elif [ -f /etc/bash_completion ]; then
. /etc/bash_completion
fi
fi
############################## 自定义 ##############################
## 变量
# 如果使用opkg,添加以下内容
#export PATH=$PATH:/opt/bin
# ----- 备忘录 -----
memo=/home/xue/文档/memo.xue
## 别名
alias ls="ls --color -F" # 自定义`ls`,可自行删减
alias lah="ls -lah" # 自定义`ls`,可自行删减
alias ll="ls -lh" # 自定义`ls`,可自行删减
alias ip='ip --color=auto' # `ip a`的彩色,很有必要
if [[ -z $memo ]]; then
alias memo="echo 备忘录路径为空!请手动添加到~/.bashrc!"
else
alias memo="lolcat $memo"
fi
alias irssi-rizon="irssi -c irc.rizon.net" # 我的`irssi`快捷配置
alias d--="c++ -x cpp"
# `thefuck`配置,安装才加载
if [[ -e /usr/bin/thefuck ]]; then
eval $( thefuck --alias f )
fi
####################################################################
# fish风格路径折叠
function _fish_collapsed_pwd() {
local pwd="$1"
local home="$HOME"
local size=${#home}
[[ $# == 0 ]] && pwd="$PWD"
[[ -z "$pwd" ]] && return
if [[ "$pwd" == "/" ]]; then
echo "/"
return
elif [[ "$pwd" == "$home" ]]; then
echo "~"
return
fi
# 替换 $HOME 为 ~
[[ "$pwd" == "$home/"* ]] && pwd="~${pwd:$size}"
# 分割路径
local IFS="/"
local elements=($pwd)
local length=${#elements[@]}
for ((i=0; i<length-1; i++)); do # 不处理最后一个元素
local elem="${elements[$i]}"
if [[ -n "$elem" ]]; then
if [[ "$elem" == .* ]]; then
# 隐藏文件夹(以 . 开头)显示前 2 个字符
elements[$i]="${elem:0:2}"
else
# 普通文件夹显示第 1 个字符
elements[$i]="${elem:0:1}"
fi
fi
done
# 重新组合路径
IFS="/"
echo "${elements[*]}"
}
# 颜色定义
RESET='\[\033[0m\]'
USER_COLOR='\[\033[1;34m\]'
HOST_COLOR='\[\033[1;33m\]'
PATH_COLOR='\[\033[1;36m\]'
GIT_COLOR='\[\033[1;32m\]'
TIME_COLOR='\[\033[0;35m\]'
SUCCESS_COLOR='\[\033[1;32m\]'
ERROR_COLOR='\[\033[1;31m\]'
PROMPT_COLOR='\[\033[1;37m\]'
# Root用户颜色
[[ $(id -u) -eq 0 ]] && USER_COLOR='\[\033[1;31m\]'
# Git分支检测
get_git_branch() {
git branch 2>/dev/null | sed -n '/^\*/s/^\* //p' | awk '{print "|"$1}'
}
############################## 精准耗时提示符 ##############################
# 智能时间格式化
format_duration() {
local ns=$1
local ms=$(( (ns + 500000) / 1000000 )) # 四舍五入到毫秒
# 强制最小显示50ms(解决终端渲染误差)
#(( ms < 50 )) && ms=50
if (( ms >= 1000 )); then
local sec=$(( ms / 1000 ))
local remainder=$(( ms % 1000 ))
if (( sec >= 60 )); then
local min=$(( sec / 60 ))
local sec_remain=$(( sec % 60 ))
if ((min >= 60)); then
local hour=$((min / 60))
local min_remain=$((min % 60))
printf "(${TIME_COLOR}%dh %02dm %02d.%03ds${RESET})" $hour $min_remain $sec_remain $remainder
else
printf "(${TIME_COLOR}%dm %02d.%03ds${RESET})" $min $sec_remain $remainder
fi
else
printf "(${TIME_COLOR}%d.%03ds${RESET})" $sec $remainder
fi
else
printf "(${TIME_COLOR}%dms${RESET})" $ms
fi
}
# 命令计时控制
__command_start_time=""
__last_prompt_time=""
trap '[[ -z "$__command_start_time" ]] && __command_start_time=$(date +%s%N)' DEBUG
set_accurate_prompt() {
local last_status=$?
local current_time=$(date +%s%N)
# 计算耗时
local duration_display=""
if [[ -n "$__command_start_time" ]]; then
local duration_ns=$((current_time - __command_start_time))
duration_display=$(format_duration "$duration_ns")
__command_start_time=""
elif [[ -n "$__last_prompt_time" ]]; then
local idle_ns=$((current_time - __last_prompt_time))
duration_display=$(format_duration "$idle_ns")
fi
# 状态指示
local status_indicator="${SUCCESS_COLOR}^o^"
(( last_status != 0 )) && status_indicator="${ERROR_COLOR}>_<:$last_status"
# 构建提示符
PS1="╭─[${USER_COLOR}\u${RESET}@${HOST_COLOR}\h${RESET}:${PATH_COLOR}$(_fish_collapsed_pwd)${RESET}${GIT_COLOR}$(get_git_branch)${RESET}]—{${status_indicator}${RESET}}—(\t)—${duration_display}"
PS1+="\n╰─${PROMPT_COLOR}\\\$${PATH_COLOR}>${RESET} "
__last_prompt_time=$current_time
}
PROMPT_COMMAND+=("set_accurate_prompt")
# 欢迎界面
if [[ -e /usr/bin/figlet ]]; then
figlet_lock_file="/tmp/figlet_lock_$$"
# 使用 $$ 作为文件名的一部分,确保每个进程都有自己的锁文件
# 检查锁文件是否存在
if [ ! -f "$figlet_lock_file" ]; then
# 创建锁文件并执行 figlet
touch "$figlet_lock_file"
echo " _ _ _
/\\_/\\ | | | (_)
(o.o) | |_| | |_
> ^ < . | _ | ( )
/ \\ . |_| |_|_|/
"
figlet "$USER! "
fi
fi
trap 'rm -f "$figlet_lock_file"' EXIT TERM # 用钩子,等退出删除锁文件
更新日志 - 重要,会发布已知BUG!
v1
这个是原本给Buildroot用的,详见Milk-V Duo S | 使用报告
v1.1
这个版本对上一版进行进一步美化。
v1.2
这一版通过以下方式优化性能,更适合资源有限的嵌入式设备!
- 上一版我使用
${date +%T}显示时间戳,这一版直接用\t; - 上一版使用的git分支引用每次调用插入,已改进。
v1.5
让第一行多出了耗时(包括空闲用时)
v1.6
- 增加了备忘录别名
memo(自行在开头备注下设置备忘录路径变量,先去掉开头“#”) - 增加了条件判断,如下:
- 如果是root用户,用户名变为 红色 警示
- 如果 备忘录路径变量 为 空,发出提示(在输入
memo的时候)
v1.8
- 增加了类似fish的路径折叠功能。
v2.1
- 优化类fish路径折叠,即父目录为单字符缩写(隐藏目录为两个字符)
- 耗时变为复合型,将整条命令的时间记录(即上条提示符命令被执行到这个提示符出现的时间,精确度为1ms)
此版本代码变少,但功能更强了!建议搭配上ble.sh使用,“口感”更加:)
BUG: 空闲时间无法显示,现为换行时间
v2.2
- 改进v2.1,使耗时的
m,s.xxxms单位之间加上空格 - 加上了边框
- 去掉了错误提示的小括号来适应边框
- 修改备忘录条件判断选项
-e(文件是否为空)改为:-z(变量是否为空)
v2.3
- 在v2.3的基础上增加了小时的换算
- 修复原本时间显示紫色括号分割性强的特点,改为白色
- 更改了ble.sh的启动逻辑,如果需要用ble.sh,建议取消注释(在自定义栏的最下面),因为ble.sh会shell嵌套,所以当
$SHLVL=2,自动退出解决问题!
在原来的基础上增加了一个
if。此外,过程中发现了一个BUG.
BUG: 在登录shell模式下,无法正常进行计算,但tty和ssh下正常
(原因:正常shell和登录shell的某个变量机制不同,导致原本[命令执行到下一个提示符出现]的时间被迫变为[命令提示符出现到下一个提示符出现]的时间……
v2.5
经过和网友的交流发现上个版本的 BUG 是因为ble.sh插件。
- 改进了上一版本的bug
- 在末尾增加了一个欢迎提示,可以安装
figlet搭配使用!
v2.6
- 发现v2.5的figlet有概率触发不了,改用文件锁的方式
- 增加
thefuck命令的if判断,就可以不用自己手动注释了
v2.7
- 增加了错误判断的表情(挺可爱的)
- 将横杠改为中文全角破折号
此外,v2.5 BUG重现!除了非登录shell无一幸免
BUG: 在登录shell模式下,无法正常进行时间计算,所有登录shell都一样……也有可能是我的shell问题,因为最近用的是Debian Sid……
v2.8
感谢hllRGB(github)帮我解决了上一版的问题,ta告诉我$PROMPT_COMMAND不是普通变量,而是数组。在原本的$PROMPT_COMMAND上增加了(" ")保证不让shell的配置打架
其次我又在=前面加上了+,成就了魔法?
-
修复了计时器问题
-
与ble.sh不太兼容!
BUG: 在 \(\text{~/.bashrc}\) 和 \(\text{/etc/bash.bashrc}\) 相同的情况下,删除 \(\text{~/.bashrc}\) 会导致计时功能不正确
v2.8.1
- 修改欢迎界面,加入小猫
- 更改欢迎界面字体,更具可读性
如果想要体验,请安装figlet~
另外,如果想要修复上一版的 BUG ,请修改 \(\text{~/.profile}\) 中刷新 \(\text{\$HOME/.bashrc}\) 的脚本全部改成 \(\text{/etc/bash.bashrc}\) 即可删除 \(\text{~/.bashrc}\) 了


浙公网安备 33010602011771号