系统运维脚本:定时采集、定时备份、远程重启、磁盘空间监控
工控设备部署在野外,你不可能天天往现场跑——运维自动化不是选择题,是必答题。
一、工控运维为什么必须自动化
工业控制设备的典型运行环境:工厂车间、户外机柜、偏远站点,7×24小时不间断运行。现场没人懂技术,出了问题只能远程排查或者派人去。如果每次数据采集、备份、磁盘清理都靠人工,那维护成本会随设备数量线性增长。
自动化运维脚本的核心目标:让设备自己照顾自己,人只管看报警和处理异常。
二、crontab定时任务配置
Linux下的定时任务调度器,每个用户一份crontab,格式固定。
2.1 crontab格式
# ┌──────── 分钟 (0-59) # │ ┌────── 小时 (0-23) # │ │ ┌──── 日 (1-31) # │ │ │ ┌── 月 (1-12) # │ │ │ │ ┌ 周 (0-7, 0和7都是周日) # │ │ │ │ │ * * * * * command2.2 特殊符号
| 符号 | 含义 | 示例 |
|---|---|---|
* | 任意值 | * * * * *每分钟 |
, | 列表 | 0,15,30,45 * * * *每15分钟 |
- | 范围 | 0 9-18 * * 1-5工作日9-18点 |
/ | 步长 | */5 * * * *每5分钟 |
2.3 常用操作
# 编辑当前用户的crontabcrontab-e# 查看当前用户的crontabcrontab-l# 系统级定时任务(直接编辑文件)vim/etc/crontab# /etc/crontab 比crontab -e多一个用户字段:# m h dom mon dow user command三、实战脚本1:定时数据采集
场景:每隔5分钟从串口读取传感器数据,存入CSV文件。
#!/bin/bash# /opt/scripts/serial_collect.sh# 串口数据采集脚本SERIAL_DEV="/dev/ttyS1"BAUDRATE="9600"DATA_DIR="/data/serial"DATE=$(date+%Y%m%d)CSV_FILE="${DATA_DIR}/sensor_${DATE}.csv"mkdir-p"$DATA_DIR"# 使用stty设置串口参数stty-F"$SERIAL_DEV""$BAUDRATE"cs8-cstopb-parenb-ixon-ixoff# 读取串口数据(3秒超时,读取一行)RAW_DATA=$(timeout3cat"$SERIAL_DEV"|head-n1)if[-z"$RAW_DATA"];thenecho"$(date'+%Y-%m-%d %H:%M:%S')[WARN] No data from serial">>"$DATA_DIR/collect.log"exit1fi# 写入CSV(首行表头自动创建)if[!-f"$CSV_FILE"];thenecho"timestamp,raw_data">"$CSV_FILE"fiecho"$(date'+%Y-%m-%d %H:%M:%S'),${RAW_DATA}">>"$CSV_FILE"echo"$(date'+%Y-%m-%d %H:%M:%S')[INFO] Data saved:${RAW_DATA}">>"$DATA_DIR/collect.log"crontab配置:
# 每5分钟采集一次*/5 * * * * /opt/scripts/serial_collect.sh四、实战脚本2:定时备份
场景:每天凌晨2点打包关键数据,保留最近7天备份。
#!/bin/bash# /opt/scripts/auto_backup.sh# 定时备份脚本BACKUP_SRC="/data/config /data/serial /opt/app"BACKUP_DST="/backup"KEEP_DAYS=7DATE=$(date+%Y%m%d_%H%M%S)BACKUP_FILE="${BACKUP_DST}/backup_${DATE}.tar.gz"LOG_FILE="${BACKUP_DST}/backup.log"mkdir-p"$BACKUP_DST"echo"$(date'+%Y-%m-%d %H:%M:%S')[INFO] Start backup...">>"$LOG_FILE"# 打包压缩tar-czf"$BACKUP_FILE"$BACKUP_SRC2>>"$LOG_FILE"if[$?-eq0];thenFILESIZE=$(du-h"$BACKUP_FILE"|awk'{print $1}')echo"$(date'+%Y-%m-%d %H:%M:%S')[OK] Backup done:${BACKUP_FILE}(${FILESIZE})">>"$LOG_FILE"elseecho"$(date'+%Y-%m-%d %H:%M:%S')[ERROR] Backup failed!">>"$LOG_FILE"exit1fi# 清理过期备份find"$BACKUP_DST"-name"backup_*.tar.gz"-mtime+${KEEP_DAYS}-deleteecho"$(date'+%Y-%m-%d %H:%M:%S')[INFO] Old backups (>${KEEP_DAYS}d) cleaned">>"$LOG_FILE"# 列出当前备份echo"--- Current backups ---">>"$LOG_FILE"ls-lh"$BACKUP_DST"/backup_*.tar.gz>>"$LOG_FILE"2>&1crontab配置:
# 每天凌晨2:00执行备份02* * * /opt/scripts/auto_backup.sh五、实战脚本3:远程重启
场景:远程通过SSH重启目标设备,重启后等待设备恢复并验证连通性。
#!/bin/bash# /opt/scripts/remote_reboot.sh# 远程重启脚本TARGET_IP="192.168.1.100"SSH_USER="root"SSH_PORT=22SSH_KEY="/root/.ssh/id_rsa"MAX_WAIT=120# 最大等待秒数CHECK_INTERVAL=5echo"$(date)[INFO] Rebooting${TARGET_IP}..."# 远程执行rebootssh-i"$SSH_KEY"-p"$SSH_PORT"-oConnectTimeout=10\-oStrictHostKeyChecking=no\"${SSH_USER}@${TARGET_IP}""sync; reboot"2>/dev/nullif[$?-ne0]&&[$?-ne255];thenecho"$(date)[ERROR] SSH command failed"exit1fiecho"$(date)[INFO] Reboot command sent, waiting for device to come back..."# 等待设备下线sleep10# 轮询检测设备恢复WAIT=0while[$WAIT-lt$MAX_WAIT];doifping-c1-W2"$TARGET_IP">/dev/null2>&1;then# 再等几秒让SSH服务起来sleep5ifssh-i"$SSH_KEY"-p"$SSH_PORT"-oConnectTimeout=5\-oStrictHostKeyChecking=no\"${SSH_USER}@${TARGET_IP}""echo ok"2>/dev/null|grep-q"ok";thenecho"$(date)[OK] Device${TARGET_IP}is back online!"# 获取设备uptime确认确实重启过ssh-i"$SSH_KEY"-p"$SSH_PORT"\"${SSH_USER}@${TARGET_IP}""uptime"2>/dev/nullexit0fifiWAIT=$((WAIT+CHECK_INTERVAL))sleep$CHECK_INTERVALecho"$(date)[INFO] Waiting... (${WAIT}s elapsed)"doneecho"$(date)[ERROR] Device${TARGET_IP}did not come back within${MAX_WAIT}s!"exit1六、实战脚本4:磁盘空间监控
场景:监控磁盘使用率,超过80%报警,超过90%自动清理旧日志。
#!/bin/bash# /opt/scripts/disk_monitor.sh# 磁盘空间监控脚本WARN_THRESHOLD=80# 报警阈值(%)CLEAN_THRESHOLD=90# 自动清理阈值(%)CLEAN_DIR="/var/log"# 待清理目录LOG_FILE="/var/log/disk_monitor.log"# 获取根分区使用率USAGE=$(df-h/|awk'NR==2 {print $5}'|tr-d'%')echo"$(date'+%Y-%m-%d %H:%M:%S')[INFO] Disk usage:${USAGE}%">>"$LOG_FILE"if["$USAGE"-ge"$CLEAN_THRESHOLD"];thenecho"$(date'+%Y-%m-%d %H:%M:%S')[WARN] Disk usage${USAGE}% >=${CLEAN_THRESHOLD}%, auto cleaning...">>"$LOG_FILE"# 清理7天前的日志文件find"$CLEAN_DIR"-name"*.log"-mtime+7-delete2>/dev/nullfind"$CLEAN_DIR"-name"*.log.*"-mtime+3-delete2>/dev/null# 清理压缩的旧日志find"$CLEAN_DIR"-name"*.gz"-mtime+3-delete2>/dev/null# 截断大日志文件(保留最后1000行)find"$CLEAN_DIR"-name"*.log"-size+50M-execsh-c\'tail -n 1000 "$1" > "$1.tmp" && mv "$1.tmp" "$1"'_{}\;# 清理后重新检测USAGE_AFTER=$(df-h/|awk'NR==2 {print $5}'|tr-d'%')echo"$(date'+%Y-%m-%d %H:%M:%S')[INFO] After cleanup:${USAGE_AFTER}%">>"$LOG_FILE"if["$USAGE_AFTER"-ge"$CLEAN_THRESHOLD"];then# 清理后仍然超标,发送报警echo"$(date'+%Y-%m-%d %H:%M:%S')[CRITICAL] Disk still full after cleanup:${USAGE_AFTER}%">>"$LOG_FILE"# 调用报警(见下一节)/opt/scripts/send_alert.sh"CRITICAL""Disk usage${USAGE_AFTER}% on$(hostname)"fielif["$USAGE"-ge"$WARN_THRESHOLD"];thenecho"$(date'+%Y-%m-%d %H:%M:%S')[WARN] Disk usage${USAGE}% >=${WARN_THRESHOLD}%!">>"$LOG_FILE"/opt/scripts/send_alert.sh"WARNING""Disk usage${USAGE}% on$(hostname)"ficrontab配置:
# 每小时检查一次磁盘0* * * * /opt/scripts/disk_monitor.sh七、报警集成
7.1 邮件报警
#!/bin/bash# /opt/scripts/send_alert.sh# 报警发送脚本(邮件 + HTTP回调)LEVEL=$1MESSAGE=$2MAIL_TO="admin@example.com"WEBHOOK_URL="https://your-api.example.com/alert"TIMESTAMP=$(date'+%Y-%m-%d %H:%M:%S')HOSTNAME=$(hostname)# 方式1:mail命令发邮件echo"[${LEVEL}]${TIMESTAMP}${HOSTNAME}:${MESSAGE}"|\mail-s"[${LEVEL}] Alert from${HOSTNAME}""$MAIL_TO"2>/dev/null# 方式2:curl调用Webhook(钉钉/企业微信/飞书等)curl-s-XPOST"$WEBHOOK_URL"\-H"Content-Type: application/json"\-d"{\"level\":\"${LEVEL}\",\"host\":\"${HOSTNAME}\",\"message\":\"${MESSAGE}\",\"timestamp\":\"${TIMESTAMP}\"}">/dev/null2>&1echo"$(date'+%Y-%m-%d %H:%M:%S')[INFO] Alert sent: [${LEVEL}]${MESSAGE}">>/var/log/alert.log7.2 钉钉机器人报警示例
# 钉钉自定义机器人WebhookDINGTALK_URL="https://oapi.dingtalk.com/robot/send?access_token=YOUR_TOKEN"curl-s"$DINGTALK_URL"\-H"Content-Type: application/json"\-d'{ "msgtype": "text", "text": { "content": "['"${LEVEL}"'] '"${HOSTNAME}"': '"${MESSAGE}"'"}}'八、日志轮转
除了脚本手动清理,Linux自带的logrotate是更规范的日志管理工具:
# /etc/logrotate.d/myapp/var/log/myapp/*.log{daily rotate7compress delaycompress missingok notifempty copytruncate size 50M}配置说明:每天轮转,保留7份,压缩旧日志,文件超过50M也轮转,copytruncate在不重启服务的情况下截断当前日志。
九、工控运维脚本部署清单
| 序号 | 脚本 | 功能 | 定时周期 | 优先级 |
|---|---|---|---|---|
| 1 | serial_collect.sh | 串口数据采集 | 5分钟 | 高 |
| 2 | auto_backup.sh | 数据备份 | 每天2:00 | 高 |
| 3 | disk_monitor.sh | 磁盘空间监控 | 每小时 | 高 |
| 4 | remote_reboot.sh | 远程重启 | 手动触发 | 中 |
| 5 | send_alert.sh | 报警通知 | 被调用 | 高 |
| 6 | logrotate | 日志轮转 | 每天 | 中 |
| 7 | ntp_sync.sh | NTP时间同步 | 每小时 | 中 |
部署步骤:
# 1. 创建脚本目录mkdir-p/opt/scripts# 2. 上传所有脚本cp*.sh /opt/scripts/chmod+x /opt/scripts/*.sh# 3. 配置crontabcrontab-e# 粘贴所有定时任务# 4. 验证脚本权限和依赖/opt/scripts/auto_backup.sh --dry-run# 5. 检查crontab服务systemctl status crond systemctlenablecrond运维脚本不追求花哨,追求可靠、可追溯、可报警。每条定时任务执行结果都要写日志,出问题能查到,这才是工控运维的基本功。