1.Mysql数据库备份脚本
(1)问题
- 备份路径是否存在
- 输入的Mysql用户名和密码,备份的数据库名称存在错误时。
- 当备份的文件超过最大范围时
(2)流程图
(3)实现
#!/bin/bash
# 提示用户输入MySQL用户名、密码、数据库名称和备份路径
read -p "请输入MySQL用户名: " MYSQL_USER
read -sp "请输入MySQL密码: " MYSQL_PASSWORD
echo
read -p "请输入要备份的数据库名称: " MYSQL_DATABASE
read -p "请输入备份文件保存的路径(例如:/path/to/backup/): " BACKUP_PATH
# 获取当前日期和时间,用于命名备份文件
CURRENT_DATETIME=$(date +%Y%m%d_%H%M%S)
#判断备份目录是否存在
if [ -d $BACKUP_PATH ]; then
echo "目录存在"
else
echo "目录不存在"
exit
fi
# 最大备份文件大小(单位:MB)
MAX_BACKUP_SIZE=500
# 创建备份文件的完整路径
BACKUP_FILE="$BACKUP_PATH/backup_$MYSQL_DATABASE_$CURRENT_DATETIME.sql"
# 使用mysqldump命令进行备份
mysqldump -u "$MYSQL_USER" -p"$MYSQL_PASSWORD" "$MYSQL_DATABASE" > "$BACKUP_FILE"
# 检查备份是否成功
if [ $? -eq 0 ]; then
echo "数据库备份成功!备份文件保存在 $BACKUP_FILE"
#备份文件大小
BACKUP_SIZE=$(du -mb "$BACKUP_FILE" | cut -f1)
if [ "$BACKUP_SIZE" -gt "$MAX_BACKUP_SIZE" ]; then
echo "备份文件 $BACKUP_FILE 大小超过了 $MAX_BACKUP_SIZE MB,正在进行压缩..."
# 使用gzip压缩备份文件
gzip "$BACKUP_FILE"
BACKUP_FILE="$BACKUP_FILE.gz"
echo "备份文件已压缩为 $BACKUP_FILE"
fi
else
echo "数据库备份失败!"
rm -rf $BACKUP_FILE
exit
fi
# 可选:删除超过7天的旧备份文件(根据需求调整)
find "$BACKUP_PATH" -type f -name "*.sql" -mtime +7 -exec rm {} \;
# 脚本结束
exit
(4)实现解析
- 使用read -p和read -sp来输入基本信息。
- CURRENT_DATETIME=$(date +%Y%m%d_%H%M%S)声明变量来获取当前时间用于命名备份文件。
- 通过[ -d $BACKUP_PATH ]来判断备份的路径是否存在。存在则继续向下执行不存在则直接退出脚本。
- 声明最大备份文件大小的变量。
- 创建备份文件的完整路径。
- 使用mysqldump命令进行备份。
- 使用$?来判断mysqldump命令的返回值,为零则备份成功,不为零则备份失败,删除创建的备份文件后退出脚本。
- 备份成功后判断文件大小,大于最大值则使用gzip压缩备份文件。使用find命令查找超过7天的旧备份文件,并使用rm将其删除。
- 使用find命令查找超过7天的旧备份文件,并使用rm将其删除。
(5)验证
1.成功
2.当文件超过最大值时。(这里将最大值调到500,实验方便)
3.当备份目录不存在时
4.当用户或密码输入错误,或数据库不存在时。
2.配置邮件系统,发送警告脚本
(1) 配置mailx
安装mailx
[root@localhost ~]# yum install -y mailx
配置/etc/mail.rc
[root@localhost ~]# cat /etc/mail.rc
添加如下几行:
set from=3222853810@qq.com
set smtp="smtps://smtp.qq.com:465"
set smtp-auth-user=3222853810@qq.com
set smtp-auth-password=izrukwaktaxncjga #这里填的是授权码或邮箱密码
set smtp-auth=login
set ssl-verify=ignore
set nss-config-dir=/etc/pki/nssdb
(2)自建信任证书
创建证书目录
[root@localhost ~]# mkdir -p /etc/pki/nssdb
获取邮件服务器证书内容
[root@localhost ~]# echo -n | openssl s_client -connect smtp.qq.com:465 | sed -ne '/-BEGIN CERTIFICATE-/,/-END CERTIFICATE-/p' > /etc/pki/nssdb/qq.crt
添加证书到数据库
[root@localhost ~]# certutil -A -n "GeoTrust SSL CA" -t "C,," -d /etc/pki/nssdb/ -i /etc/pki/nssdb/qq.crt
[root@localhost ~]# certutil -A -n "GeoTrust Global CA" -t "C,," -d /etc/pki/nssdb/ -i /etc/pki/nssdb/qq.crt
列出指定目录下的证书
[root@localhost ~]# certutil -L -d /etc/pki/nssdb/
进入证书目录
[root@localhost ~]# cd /etc/pki/nssdb/
指名受信任证书
[root@localhost nssdb]# certutil -A -n "GeoTrust SSL CA - G3" -t "Pu,Pu,Pu" -d ./ -i qq.crt
Notice: Trust flag u is set automatically if the private key is present. #出现这句提示就可以
(3)编写警告脚本
#!/bin/bash
# 告警信息
subject="系统告警"
body="系统检测到异常,请尽快处理。"
to_email="3222853810@qq.com" # 替换为接收告警的邮箱地址
# 发送邮件
echo "$body" | mail -s "$subject" "$to_email"
(4)执行测试脚本
[root@localhost ~]# sh e.sh
[root@localhost ~]# smtp-server: "/root/dead.letter" 0/0
. . . message not sent.
3.批量检测网站是否异常并邮寄通知
(1)问题
- 输入的网址不存在。
- 输入的网址存在异常
(2)分析
- 如果使用mail命令发送邮件,需要确保系统已配置好邮件发送服务。
- 创建一个文件用于添加需要检查的网站
- 使用curl用于发送HTTP请求并获取状态码。
(3)流程图
(4)实现
#!/bin/bash
# 配置部分
URL_FILE="urls.txt" # 包含要检测的URL列表的文件
LOG_FILE="check_urls.log" # 日志文件路径
EMAIL="3222853810@qq.com" # 接收通知邮件的邮箱地址
RETRIES=3 # 对每个URL的重试次数
TIMEOUT=5 # curl连接超时时间(秒)
# 清空日志文件(如果存在)
> "$LOG_FILE"
# 读取URL列表并检查每个URL
while IFS= read -r URL; do
echo "$(date): Checking $URL" >> "$LOG_FILE"
FAIL_COUNT=0
for ((i=1; i<=$RETRIES; i++)); do
HTTP_CODE=$(curl -o /dev/null --connect-timeout "$TIMEOUT" -s -w "%{http_code}\n" "$URL" 2>>"$LOG_FILE")
# 检查curl命令是否成功执行(返回0表示成功)
if [[ $? -ne 0 ]]; then
echo "$(date): 检查URL时出错(curl命令失败)" >> "$LOG_FILE"
FAIL_COUNT=$RETRIES # 设置为RETRIES以触发邮件发送
break
fi
# 检查HTTP状态码
if [[ $HTTP_CODE -ge 200 && $HTTP_CODE -lt 400 ]]; then # 通常成功的状态码范围
echo "$(date): $URL is ok (HTTP $HTTP_CODE)" >> "$LOG_FILE"
break # 成功,跳出循环
else
echo "$(date): $URL failed (HTTP $HTTP_CODE), retry $i" >> "$LOG_FILE"
FAIL_COUNT=$((FAIL_COUNT + 1))
fi
done
# 如果所有尝试都失败了,则发送邮件通知
if [[ $FAIL_COUNT -eq $RETRIES ]]; then
echo '网站异常' |mail -s '警告' $EMAIL
fi
done < $URL_FILE
echo "URL已检查完成,详细请参阅check_urls.log文件"
(5)解析
(1)配置部分
URL_FILE=”urls.txt”:指定包含要检查的URL列表的文件名。
LOG_FILE=“check_urls.log”:指定用于记录日志的文件名。
EMAIL=”3222853810@qq.com”:指定接受警告邮件的邮箱地址。
RETRIES=3:设置对每个URL的重试次数。
TIMEOUT=5:设置curl命令的链接超市时间。(以秒为单位)
(2)清空日志文件
> “$LOG_FILE”:使用重定向操作符>来清空(或创建)日志文件。
(3)读取URL列表
while IFS= read -r URL; do......done < $URL_FILE :逐行读取URL_FILE文件中的URL并赋值给变量URL;IFS=读取行的时候不会基于任何特定的字符来分割字段。在读取行时,确保了整行的内容被完整的赋值给变量。read -r URL:将读取的行的内容赋值给变量。
(4)循环内部
echo "$(date): Checking $URL" >> "$LOG_FILE"
FAIL_COUNT=0
在日志文件中记录开始检查某个URL的时间。
初始化失败计数器。
(5)重试循环
for ((i=1; i<=$RETRIES; i++)); do使用for循环进行重试,次数有RETRIES变量指定。
(6)使用curl命令并检查状态码
HTTP_CODE=$(curl -o /dev/null --connect-timeout "$TIMEOUT" -s -w "%{http_code}\n" "$URL" 2>>"$LOG_FILE")
使用 curl 命令检查 URL,并将 HTTP 状态码存储在 HTTP_CODE 变量中。
-o /dev/null 将输出重定向到 /dev/null(即忽略输出)。
--connect-timeout "$TIMEOUT" 设置连接超时时间。
-s 使 curl 静音(不显示进度条或错误消息)。
-w "%{http_code}\n" 只打印 HTTP 状态码。
2>>"$LOG_FILE" 将 curl 的错误消息重定向到日志文件。
(7)检查curl命令是否执行成功
检查curl命令的退出状态,如果curl命令失败,记录并在日志中标记该URL为失败,然后跳出循环。
(8)检查HTTP状态码
如果HTTP状态码在200到399之间,记录成功病跳出循环。
否则,记录失败并增加失败计数器。
(9)发送邮件通知
如果失败计数器等于重试次数,发送邮件通知。
注意:这里使用了 mail 命令发送邮件,但它可能需要额外的配置(如邮件服务器设置)才能在您的系统上正常工作。
(10)done < $URL_FILE
结束while循环,继续从URL_FILE文件中读取下一行。
(11)也可以设置脚本定期执行
使用 crontab -e 命令来编辑当前用户的 crontab 文件
每分钟执行一次
(6)验证
首先将要检查的网址添加到文件中。
执行脚本,检查日志。
当检查的网址不存在时
查看日志文件
当访问的网址HTTP码不在200-399之间时
查看日志
4.输入网卡的名字,来输出网卡的IP
(1)问题
- 输入的字符不符合网卡名字规范。
- 名字符合规范,但是根本没有这个网卡。
- 输入网卡有多个IP地址。
(2)分析
- 把本机的所有网卡名列出来,来引导用户输入。
- 使用命令列出所有网卡信息。
- 设计一个函数,把网卡名字作为参数,函数的返回值是网卡的IP。
- 在获取某个IP是,考虑网卡有多个IP地址(或为空的IP)。
(3)流程图
(4)实现
#!/bin/bash
# 把本机的所有网卡名列出来,来引导用户输入。
get_interfaces() {
ip -o -4 addr show | awk '{print $2}' | cut -d/ -f1
}
# 显示网卡名并提示用户输入
echo "可用的网卡有:"
IFS=$'\n' interfaces=($(get_interfaces)) # 将网卡名存储在数组中
unset IFS # 恢复默认的IFS值
for iface in "${interfaces[@]}"; do
echo " - $iface"
done
# 检查用户输入
read -p "请输入网卡名: " user_input
# 检查网卡名是否有效(即是否在列出的网卡中)
if ! [[ " ${interfaces[*]} " =~ " ${user_input} " ]]; then
echo "错误:输入的网卡名不符合规范或网卡不存在。"
exit 1
fi
# 设计一个函数,把网卡名作为参数,函数返回网卡的IP列表
get_ip_addresses() {
local iface=$1
# 使用 ip addr 命令获取指定网卡的IP地址列表
ip -4 addr show "$iface" | grep -oP '(?<=inet\s)\d+(\.\d+){3}'
}
# 在获取某个网卡IP时,考虑网卡有多个IP地址(或为空IP的网卡,但这种情况很少见且通常表示网卡未配置)
# 调用函数并输出结果
ip_addresses=($(get_ip_addresses "$user_input"))
if [ ${#ip_addresses[@]} -eq 0 ]; then
echo "网卡 $user_input 没有配置IPv4地址。"
else
echo "网卡 $user_input 的IPv4地址是:"
for ip in "${ip_addresses[@]}"; do
echo " - $ip"
done
fi
(5)实现分析
列出网卡名:
使用ip -o -4 addr show命令列出所有网卡的IPv4地址及其接口名。
通过awk和cut命令提取网卡名,并存储在数组中。
遍历数组,显示网卡名列表给用户。
用户输入与检查:
提示用户输入网卡名。
使用[[ " ${interfaces[*]} " =~ " ${user_input} " ]]语法检查用户输入的网卡名是否在列出的网卡中。这种方法利用了Bash的模式匹配功能,通过空格来确保精确匹配。
获取IP地址:
使用ip -4 addr show命令和正则表达式提取用户指定网卡的所有IPv4地址。
将获取到的IP地址存储在数组中。
输出结果:
判断存储IP地址的数组是否为空。
如果为空,则输出网卡没有配置IPv4地址的信息。
如果不为空,则遍历数组,输出每个IP地址。
(6)验证
1.正确
[root@localhost ~]# sh d.sh
可用的网卡有:
- lo
- ens33
请输入网卡名: ens33
网卡 ens33 的IPv4地址是:
- 192.168.63.37
2输入错误的网卡名字时
[root@localhost ~]# sh d.sh
可用的网卡有:
- lo
- ens33
请输入网卡名: ens36
错误:输入的网卡名不符合规范或网卡不存在。
以上举了几个简单脚本案例供大家参考。