文章目录
前言
说实话,这是我第一次用Shell来定义函数,之前也写了很多shell脚本,但是体量都不大,所以基本上是按照需求罗列了多个命令来实现的,这次也是一样,但是我发现重复的地方太多了,所以还是要拿出看见本事“抽象函数”来解放我懒惰的手指
具体需求
检测特定名称的进程是否存在,若不存在则重新启动这个进程
仿照着之前的类似的脚本我写出了以下函数 check_and_fix_process
,仅有一个需要注意的点就是Shell函数不需要定义参数,如果用到参数直接是用 $1
、 $2
、 $3
……依次来代替就可以了
#!/bin/bash
# 检查并修复进程的函数
function check_and_fix_process() {
# $1 进程名
# $2 进程ID列表文件名
# $3 进程ID列表文件md5值
datetime=$(date +%y%m%d%H%M%S)
ps aux |grep "$1" |grep -v grep |awk '{print $15}' |awk -F '=' '{print $2}'|sort -n > ~/tmplist
a=$(md5sum ~/tmplist |awk '{print $1}')
b="$3"
if [[ $a = $b ]]; then
echo "check [$1 $2 $3] ok"
else
tmp=$(diff ~/"$2" ~/tmplist |grep ^\< |awk '{print $2}' > /tmp/tmplist)
for i in `cat /tmp/tmplist`
do
cd ~/test && grep "ID=$i" start.sh | xargs -I {} sh -c '{}'
echo "$datetime $i" >>~/fixtxt
python3 ~/send_msg.py -c "process:$i crashed; fixtime:$datetime"
done
fi
}
# check all process list
check_and_fix_process "AProcess" "aprocesslist" "a887eedb72472f2ad152e5e91a0727da"
check_and_fix_process "BProcess" "bprocesslist" "a887eedb72472f2ad152e5e91a0727db"
ChatGPT读代码
如果对于这段代码有不理解的地方,可以请ChatGPT来帮忙,以下内容是它的解释,不得不说真是太强大了!身为此段代码的实现者,我都描述不了这么详细
这段代码是一个 Bash 脚本,用于检查指定的进程是否正常运行,并在发现异常时进行修复操作。下面逐行解释代码:
-
function check_and_fix_process() {
: 定义了一个名为check_and_fix_process
的 Bash 函数。 -
# $1 进程名
: 这是一个注释,表示函数的第一个参数是进程名。 -
# $2 进程ID列表文件名
: 这是一个注释,表示函数的第二个参数是进程ID列表文件的文件名。 -
# $3 进程ID列表文件md5值
: 这是一个注释,表示函数的第三个参数是进程ID列表文件的MD5值。 -
datetime=$(date +%y%m%d%H%M%S)
: 获取当前日期和时间,并将其格式化为"YYMMDDHHMMSS"的形式,存储在变量datetime
中。 -
ps aux |grep "$1" |grep -v grep |awk '{print $15}' |awk -F '=' '{print $2}'|sort -n > ~/tmplist
: 这一行通过一系列的管道命令来查找指定进程名$1
的进程,提取其中的某个列(可能是进程ID),然后排序,将结果保存到文件~/tmplist
中。 -
a=$(md5sum ~/tmplist |awk '{print $1}')
: 计算文件~/tmplist
的 MD5 值,并将结果保存在变量a
中。 -
b="$3"
: 将第三个参数值(进程ID列表文件的MD5值)保存在变量b
中。 -
if [[ $a = $b ]]; then
: 如果变量a
的值等于变量b
的值(即进程ID列表文件的MD5值相匹配),则执行下面的代码块。 -
echo "check [$1 $2 $3] ok"
: 输出一条信息表示检查通过。 -
else
: 如果进程ID列表文件的MD5值不匹配,则执行下面的代码块。 -
tmp=$(diff ~/"$2" ~/tmplist |grep ^\< |awk '{print $2}' > /tmp/tmplist)
: 比较进程ID列表文件(路径为~/"$2"
)和当前的进程ID列表文件 (~/tmplist
),将不匹配的部分提取出来并保存在临时文件/tmp/tmplist
中。 -
for i in $(cat /tmp/tmplist)
: 循环遍历临时文件/tmp/tmplist
中的每一行内容。 -
do
: 循环体开始。 -
cd ~/test && grep "ID=$i" start.sh | xargs -I {} sh -c '{}'
: 这一行的作用是切换到目录~/test
并在start.sh
文件中查找包含字符串 “ID=$i” 的行,然后执行找到的行(通常是一些命令)。 -
echo "$datetime $i" >>~/fixtxt
: 将当前日期时间和进程ID添加到文件~/fixtxt
中。 -
python3 ~/send_msg.py -c "process:$i crashed; fixtime:$datetime"
: 调用 Python 脚本send_msg.py
并传递一条消息,该消息包含进程ID以及修复操作的时间。 -
done
: 循环结束。 -
fi
: 条件分支结束。 -
}
: 函数定义结束。 -
check_and_fix_process "AProcess" "aprocesslist" "a887eedb72472f2ad152e5e91a0727da"
: 调用check_and_fix_process
函数,检查名为 “AProcess” 的进程是否正常运行,使用文件 “aprocesslist” 作为进程ID列表文件,并传递预期的MD5值。 -
check_and_fix_process "BProcess" "bprocesslist" "a887eedb72472f2ad152e5e91a0727db"
: 同上,检查名为 “BProcess” 的进程是否正常运行,使用文件 “bprocesslist” 作为进程ID列表文件,并传递预期的MD5值。
总结
- Shell脚本中的函数不需要定义参数,如果用到参数直接是用
$1
、$2
、$3
……依次来代替就可以 - Shell脚本函数中使用 $1 作为参数,并不会与内部命令的 $1 冲突,因为Shell在不同的上下文中,变量的作用域是不同的
看我ge,看我nai,看我jiu,玩的开心吗?