背景
最近工作中使用的自动化脚本涉及的一个功能是通过shell脚本来控制进程的重启(因为自己以前写过, 但是因为归纳总结做的不到位,导致找不到原来的笔记了)只能从网上搜下大概的,然后根据自己的理解重新整理下了, 整理的同时也复习了一下基本的shell脚本的编写, 做到温故知新!
本次的需求: 实现一个shell脚本来控制服务的启动, 如果该服务之前未运行, 通过该脚本可将服务运行起来;如果该服务已处于运行状态, 那么通过该脚本可将服务重新启动!
环境部署
本文使用的服务就拿tomcat服务来举例了, 毕竟这个服务下载和安装和部署都相对容易些
tomcat下载地址
https://downloads.apache.org/tomcat/tomcat-9/v9.0.62/bin/
tomcat部署
- 先解压文件 tar -zxvf apache-tomcat-9.0.62.tar.gz
- 进入目录, 运行tomcat cd apache-tomcat-9.0.62/bin
- 运行 启动命令: sh startup.sh 结束命令: sh shutdown.sh
- 预期结果 可能报错
「预期结果」 通过ps -ef|grep tomcat 命令, 即可查看到tomcat进程信息
「最常见的报错」 8080端口被占用了,因为tomcat默认端口就是8080 此时可以通过 lsof -i:8080, 找到该进程的pid, 然后kill -9 pid即可结束掉该进程, 重新运行 sh startup.sh 即可
重启tomcat的shell脚本
自己调试的最终版本代码如下
代码语言:javascript复制pid=$(ps -ef | grep tomcat|grep -v grep| awk '{print $2}')
if [ ! -z "$pid" ];then
echo "当前运行tomcat服务的pid是: ${pid}"
kill -9 ${pid}
echo -e "已结束当前tomcat服务~n"
else
echo -e "目前未运行tomcat服务!n"
fi
sh startup.sh
echo -e "n"
pid1=$(ps -ef | grep tomcat|grep -v grep| awk '{print $2}')
if [ ! -z "$pid1" ];then
echo "已重启tomcat服务( * ̄▽ ̄)"
echo "tomcat服务新的pid是: ${pid1}"
else
echo "重启tomcat服务失败, 请检查是不是8080端口被占用了(>﹏<)"
fi
将上述代码命名为restart.sh, 放在了tomcat的bin目录下
- 测试场景 - 之前「未」启动服务,此时运行该脚本
- 测试场景 - 之前「已」启动服务,此时运行该脚本
本次的shell代码知识点
ps -ef 那一长串命令的解释
代码语言:javascript复制ps -ef | grep tomcat|grep -v grep| awk '{print $2}'
- 首先 ps -ef | grep tomcat是过滤当前系统中, 带有tomcat关键字的所有进程
- 由上图可见, 查询出来2条进程, 一个是预期的tomcat进程,另一个是我们过滤的grep进程.我们需要把grep进程过滤掉, 所以使用 grep -v grep
- 备注: grep -v 是反向查找的意思,比如 grep -v grep 就是查找不含有 grep 字段的行
- 经过上述操作,我们仅查出来一个预期进程, 我们目标是获取以空格分割的的第二列数据 27851 这个进程号, 所以使用到了awk命令
- 备注: 传闻Linux中有三剑客: grep, sed, awk.这里用到的awk是linux三剑客之一!
- awk的使用场景是想获取以某个分隔符分割的数据,这个分隔符默认是空格. print $2 代表取第2列的数据,即当前场景的进程号 27851
shell中为变量赋值 和 取值
使用的是() 和 变量 这两种用法
- 基本示例示例
a=$(date)
echo $a # Wed Apr 20 20:50:48 CST 2022
- tomcat的shell脚本中
pid=$(ps -ef | grep tomcat|grep -v grep| awk '{print $2}')即将各种操作后得到的pid赋值给pid变量
shell判空
if [ ! -z "$pid" ];then
这句代码里面用到了判空的用法, 如果 从pid变量取出的值为空, 那么if [ -z "$pid" ];then
就为True, 加上!, 代表去反则为False
pid=$(ps -ef | grep tomcat|grep -v grep| awk '{print $2}')
if [ ! -z "$pid" ];then
echo "当前运行tomcat服务的pid是: ${pid}"
kill -9 ${pid}
echo -e "已结束当前tomcat服务~n"
else
echo -e "目前未运行tomcat服务!n"
fi
在本代码块中, 如果能查找到tomcat的pid, 那么if [ -z "$pid" ];then
为Fasel, 去反为True, 进入到then后面的判断语句, 根据tomcat的pid结束掉tomcat进程
shell的其它小细节
- 「双引号 和 单引号的区别」
双引号: 里面可以调用变量, 相当于动态使用变量.if [ ! -z "$pid" ]
可以动态的获取pid变量的值放入判断语句中
单引号: 将里面的内容就认为是一个字符串, 不会动态的使用里面的变量的值.例如,echo 'pid',输出结果为 pid
- 「shell脚本中输出换行符」
一开始以为直接这样既可echo "hello worldn"
, 发现并不可以, 必须这样使用echo -e "hello worldn"
.其中-e参数代表激活转义字符