#!/bin/bash# # Jenkins 服务中断 · 系统化排查脚本哲学增强版# 哲学基石本体论定性 → 奥卡姆筛选 → 辩证决策 → 实用进化 → 无为防御 → 整体洞察# set-opipefail# ---------- 可配置变量实用主义根据你的环境调整----------JENKINS_HOME${JENKINS_HOME:-/var/lib/jenkins}JENKINS_PORT${JENKINS_PORT:-8080}JENKINS_USER${JENKINS_USER:-jenkins}LOG_LINES50# 抓取日志行数HIGH_DISK_THRESHOLD90# 磁盘使用率告警阈值%# 颜色输出RED\033[0;31mGREEN\033[0;32mYELLOW\033[1;33mNC\033[0m# ---------- 1. 本体论定性精确锁定“中断”的本质 ----------echo-e${GREEN} 第一步本体论定性 —— 定义故障实体 ${NC}# 1.1 进程是否存在ifpgrep-u$JENKINS_USER-fjenkins/dev/null21;thenJENKINS_PID$(pgrep-u$JENKINS_USER-fjenkins|head-1)echo-e${GREEN}[进程] 存在 (PID:$JENKINS_PID)${NC}PROCESS_EXISTStrueelseecho-e${RED}[进程] 不存在${NC}PROCESS_EXISTSfalsefi# 1.2 端口是否响应超时 3 秒iftimeout3bash-cecho /dev/tcp/localhost/$JENKINS_PORT2/dev/null;thenecho-e${GREEN}[端口]$JENKINS_PORT可达${NC}PORT_OPENtrueelseecho-e${RED}[端口]$JENKINS_PORT不可达${NC}PORT_OPENfalsefi# 1.3 最后一次活动时间systemd 管理的服务ifsystemctl is-active jenkins/dev/null21;thenecho-e${YELLOW}[systemd] 服务状态: active${NC}elseecho-e${RED}[systemd] 服务状态: inactive / failed${NC}fi# 【手工检验注释】# 若进程存在但端口不可达 → 可能是假死hang需查看线程栈 jstack -l $JENKINS_PID# 若进程完全消失 → 进入第二步查找致命信号重点看 OOM / 磁盘。echo# ---------- 2. 奥卡姆剃刀致命信号层一击致命 ----------echo-e${GREEN} 第二步奥卡姆剃刀 —— 致命信号层 ${NC}FATAL_SIGNAL_FOUNDfalse# 2.1 OOM Killerecho[检查] 内核 OOM Killer 记录...OOM_LOG$(dmesg-T2/dev/null|grep-iout of memory.*java|tail-5)if[-n$OOM_LOG];thenecho-e${RED}[致命] 发现 OOM 记录Jenkins 被系统杀死。${NC}echo$OOM_LOGFATAL_SIGNAL_FOUNDtrueelse# 也检查 /var/log/messages某些发行版OOM_LOG2$(grep-iout of memory.*java/var/log/messages2/dev/null|tail-5)if[-n$OOM_LOG2];thenecho-e${RED}[致命] /var/log/messages 中发现 OOM 记录${NC}echo$OOM_LOG2FATAL_SIGNAL_FOUNDtrueelseecho[OOM] 未发现明显 OOM 记录fifi# 2.2 磁盘空间echo[检查] 磁盘空间 (JENKINS_HOME 及关键分区)...DISK_FULLfalseforPARTin/$JENKINS_HOME/tmp /var;doif[-d$PART];thenUSAGE$(df-h$PART|awkNR2 {print $5}|seds/%//)INODE_USAGE$(df-i$PART|awkNR2 {print $5}|seds/%//)if[$USAGE-ge$HIGH_DISK_THRESHOLD];thenecho-e${RED}[致命]$PART磁盘使用率${USAGE}% (阈值${HIGH_DISK_THRESHOLD}%)${NC}FATAL_SIGNAL_FOUNDtrueDISK_FULLtruefiif[$INODE_USAGE-ge$HIGH_DISK_THRESHOLD];thenecho-e${RED}[致命]$PARTinode 使用率${INODE_USAGE}% (可能小文件耗尽)${NC}FATAL_SIGNAL_FOUNDtruefifidoneif!$DISK_FULL;thenecho[磁盘] 空间与 inode 正常fi# 2.3 文件句柄仅当进程存在时检查if$PROCESS_EXISTS;thenFD_COUNT$(ls/proc/$JENKINS_PID/fd2/dev/null|wc-l)FD_LIMIT$(grepMax open files/proc/$JENKINS_PID/limits2/dev/null|awk{print $4})if[-n$FD_LIMIT][$FD_COUNT-ge$((FD_LIMIT*80/100))];thenecho-e${RED}[致命] 文件句柄使用量接近上限:$FD_COUNT/$FD_LIMIT${NC}FATAL_SIGNAL_FOUNDtrueelseecho[句柄] 正常 ($FD_COUNT/$FD_LIMIT)fifi# 2.4 JVM 崩溃日志echo[检查] JVM 致命错误日志...HS_ERR$(find$JENKINS_HOME/tmp /var/log-namehs_err_pid*-mmin-602/dev/null|head-1)if[-n$HS_ERR];thenecho-e${RED}[致命] 发现 JVM 崩溃日志:$HS_ERR${NC}head-20$HS_ERRFATAL_SIGNAL_FOUNDtrueelseecho[JVM] 未发现 hs_err_pid 文件fi# 奥卡姆剃刀决策点若已发现致命信号可立即提示if$FATAL_SIGNAL_FOUND;thenechoecho-e${YELLOW}★★★ 奥卡姆剃刀结论已捕获致命信号建议直接针对上述发现处理无需继续深挖。★★★${NC}# 【手工检验注释】# - 若是 OOM用 free -h、ps aux --sort-%mem | head 分析内存分布# - 若是磁盘满用 du -sh /var/lib/jenkins/jobs/*/builds/* | sort -rh | head 找出大目录# - 若为 JVM 崩溃检查 hs_err 文件中 Internal Error 和 Stack 段考虑 JDK 版本与插件兼容性# 然后按辩证决策第三步决定立即重启还是继续取证。fiecho# ---------- 3. 辩证决策恢复 vs 深挖 ----------echo-e${GREEN} 第三步辩证决策 —— 恢复与根因的权衡 ${NC}# 尝试简单判断是否处于业务高峰例如当前时间HOUR$(date%H)if[$HOUR-ge9][$HOUR-le18];thenPEAK_TIMEtrueecho[时间] 当前处于业务高峰时段 (9-18点)elsePEAK_TIMEfalseecho[时间] 当前处于低峰时段fi# 【手工检验注释】# 这里需要人工介入决策。脚本仅给出建议# 若为业务高峰且致命信号已明确建议立即执行预案恢复但务必先执行以下命令保存现场# journalctl -u jenkins --since 30 minutes ago /tmp/jenkins_crash_snapshot.log# cp -r /var/lib/jenkins /tmp/jenkins_home_backup_$(date %Y%m%d_%H%M) # 注意磁盘空间# 然后重启服务 systemctl restart jenkins# 若为低峰或致命信号不明确请继续执行本脚本的后续深度分析部分。echoread-p是否继续深度分析(y/n默认 y): CONTINUECONTINUE${CONTINUE:-y}if[$CONTINUE!y];thenecho已跳过深度分析。请根据需要重启服务或人工介入。exit0fi# ---------- 4. 整体论与深度分析 ----------echo-e${GREEN} 第四步整体论深度分析 —— 关联与涌现行为 ${NC}# 4.1 Jenkins 自身日志最近的错误echo[日志] 抓取 Jenkins 服务日志最后$LOG_LINES行...journalctl-ujenkins --no-pager-n$LOG_LINES2/dev/null||\tail-n$LOG_LINES$JENKINS_HOME/../jenkins.log2/dev/null||\echo无法获取 Jenkins 日志请手工检查 /var/log/jenkins/# 4.2 系统资源全景关联 OOM 时刻echoecho[系统] 内存与 Swap 现状free-hechoecho[系统] 当前 CPU 负载与进程 Top 5top-bn1|head-15echoecho[系统] 当前磁盘 I/O 等待iostat-x122/dev/null|tail-20||echoiostat 未安装# 4.3 依赖连通性检查整体论视角echoecho[依赖] 测试关键外部服务连通性...# Git 仓库连通性示例GIT_REPO$(grep-rgit$JENKINS_HOME/jobs-l2/dev/null|head-1)if[-f$GIT_REPO];thenREMOTE_URL$(grep-oP(?url)[^]$GIT_REPO|head-1)if[-n$REMOTE_URL];thentimeout5gitls-remote$REMOTE_URL/dev/null21\echo[Git]$REMOTE_URL可达||\echo-e${RED}[Git]$REMOTE_URL不可达${NC}fielseecho[Git] 未找到仓库配置跳过fi# 检查本地端口占用情况监控系统滥用短连接echoecho[网络] TIME_WAIT 连接数量ss-s|grep-itimewait||echo无 TIME_WAIT 统计# 【手工检验注释】# - 若怀疑某个外部依赖如 Git、Nexus拖慢 Jenkins可用 telnet/tcping 测试延迟。# - 若 TIME_WAIT 数量极高数千考虑优化内核参数或调整监控频率。# - 使用 eBPF 工具进一步分析sudo filetop -C 5 可实时看到哪个进程在写盘最多。echo# ---------- 5. 数据完整性当进程尝试启动但立即退出时必需----------echo-e${GREEN} 第五步数据完整性检查 ${NC}if$PROCESS_EXISTS;thenecho进程尚存跳过数据完整性检查。若要验证请先停止 Jenkins。else# 尝试前台启动并捕获错误只运行5秒用于诊断echo[数据] 尝试前台启动 Jenkins 5 秒以捕获配置错误...sudo-u$JENKINS_USERtimeout5java-jar/usr/share/jenkins/jenkins.war\--httpPort$JENKINS_PORT--webroot/var/cache/jenkins/war\21|tee/tmp/jenkins_foreground.logechoecho[数据] 常见错误检查grep-isaxparse\|xstream\|config.xml/tmp/jenkins_foreground.log\echo-e${RED}发现 XML 配置损坏请恢复备份或检查对应文件${NC}||\echo未发现 XML 解析错误grep-inoclassdeffound\|linkageerror/tmp/jenkins_foreground.log\echo-e${RED}发现插件冲突或类加载错误考虑进入安全模式或移除最近更新的插件${NC}||\echo未发现插件冲突fi# 【手工检验注释】# 若前台启动报错定位到具体文件如 /var/lib/jenkins/jobs/xxx/config.xml 损坏# cp /var/lib/jenkins/jobs/xxx/config.xml /var/lib/jenkins/jobs/xxx/config.xml.bak# 然后尝试用空白配置替换或手动修复 XML。# 若为插件冲突可暂时移动插件 mv /var/lib/jenkins/plugins/xxx.jpi /tmp/echo# ---------- 6. 无为防御展示当前自愈配置 ----------echo-e${GREEN} 第六步无为防御 —— 自愈配置现状 ${NC}echo[cron] 检查磁盘清理任务...crontab-l2/dev/null|grep-ijenkins\|clean\|disk||echo未找到相关 cron 任务建议添加磁盘自动清理echo[systemd] 检查内存限制...ifsystemctlcatjenkins2/dev/null|grep-qMemoryMax\|MemoryHigh;thensystemctlcatjenkins2/dev/null|grep-EMemoryMax|MemoryHighelseecho未设置 MemoryMax/MemoryHigh建议为 Jenkins 配置内存限制以防 OOMfiecho[健康检查] 建议配置 Jenkins 健康检查端点 (如 /login)# 【手工检验注释】# 无为防御的最佳实践# - 添加 cron: 0 3 * * * find /var/lib/jenkins/jobs/*/builds -maxdepth 0 -mtime 7 -exec rm -rf {} \;# - 编辑 /etc/systemd/system/jenkins.service.d/override.conf 添加:# [Service]# MemoryHigh4G# MemoryMax5G# - 使用 systemd 的 ExecStartPre 校验关键 XML:# ExecStartPre/usr/bin/xmllint --noout /var/lib/jenkins/config.xmlechoecho-e${GREEN} 排查脚本执行完毕 ${NC}echo请根据上述输出定位根因。若为致命信号且已执行恢复请将本次日志保存用于事后分析。
Linux下Jenkins数据故障的系统化排查Shell脚本
#!/bin/bash# # Jenkins 服务中断 · 系统化排查脚本哲学增强版# 哲学基石本体论定性 → 奥卡姆筛选 → 辩证决策 → 实用进化 → 无为防御 → 整体洞察# set-opipefail# ---------- 可配置变量实用主义根据你的环境调整----------JENKINS_HOME${JENKINS_HOME:-/var/lib/jenkins}JENKINS_PORT${JENKINS_PORT:-8080}JENKINS_USER${JENKINS_USER:-jenkins}LOG_LINES50# 抓取日志行数HIGH_DISK_THRESHOLD90# 磁盘使用率告警阈值%# 颜色输出RED\033[0;31mGREEN\033[0;32mYELLOW\033[1;33mNC\033[0m# ---------- 1. 本体论定性精确锁定“中断”的本质 ----------echo-e${GREEN} 第一步本体论定性 —— 定义故障实体 ${NC}# 1.1 进程是否存在ifpgrep-u$JENKINS_USER-fjenkins/dev/null21;thenJENKINS_PID$(pgrep-u$JENKINS_USER-fjenkins|head-1)echo-e${GREEN}[进程] 存在 (PID:$JENKINS_PID)${NC}PROCESS_EXISTStrueelseecho-e${RED}[进程] 不存在${NC}PROCESS_EXISTSfalsefi# 1.2 端口是否响应超时 3 秒iftimeout3bash-cecho /dev/tcp/localhost/$JENKINS_PORT2/dev/null;thenecho-e${GREEN}[端口]$JENKINS_PORT可达${NC}PORT_OPENtrueelseecho-e${RED}[端口]$JENKINS_PORT不可达${NC}PORT_OPENfalsefi# 1.3 最后一次活动时间systemd 管理的服务ifsystemctl is-active jenkins/dev/null21;thenecho-e${YELLOW}[systemd] 服务状态: active${NC}elseecho-e${RED}[systemd] 服务状态: inactive / failed${NC}fi# 【手工检验注释】# 若进程存在但端口不可达 → 可能是假死hang需查看线程栈 jstack -l $JENKINS_PID# 若进程完全消失 → 进入第二步查找致命信号重点看 OOM / 磁盘。echo# ---------- 2. 奥卡姆剃刀致命信号层一击致命 ----------echo-e${GREEN} 第二步奥卡姆剃刀 —— 致命信号层 ${NC}FATAL_SIGNAL_FOUNDfalse# 2.1 OOM Killerecho[检查] 内核 OOM Killer 记录...OOM_LOG$(dmesg-T2/dev/null|grep-iout of memory.*java|tail-5)if[-n$OOM_LOG];thenecho-e${RED}[致命] 发现 OOM 记录Jenkins 被系统杀死。${NC}echo$OOM_LOGFATAL_SIGNAL_FOUNDtrueelse# 也检查 /var/log/messages某些发行版OOM_LOG2$(grep-iout of memory.*java/var/log/messages2/dev/null|tail-5)if[-n$OOM_LOG2];thenecho-e${RED}[致命] /var/log/messages 中发现 OOM 记录${NC}echo$OOM_LOG2FATAL_SIGNAL_FOUNDtrueelseecho[OOM] 未发现明显 OOM 记录fifi# 2.2 磁盘空间echo[检查] 磁盘空间 (JENKINS_HOME 及关键分区)...DISK_FULLfalseforPARTin/$JENKINS_HOME/tmp /var;doif[-d$PART];thenUSAGE$(df-h$PART|awkNR2 {print $5}|seds/%//)INODE_USAGE$(df-i$PART|awkNR2 {print $5}|seds/%//)if[$USAGE-ge$HIGH_DISK_THRESHOLD];thenecho-e${RED}[致命]$PART磁盘使用率${USAGE}% (阈值${HIGH_DISK_THRESHOLD}%)${NC}FATAL_SIGNAL_FOUNDtrueDISK_FULLtruefiif[$INODE_USAGE-ge$HIGH_DISK_THRESHOLD];thenecho-e${RED}[致命]$PARTinode 使用率${INODE_USAGE}% (可能小文件耗尽)${NC}FATAL_SIGNAL_FOUNDtruefifidoneif!$DISK_FULL;thenecho[磁盘] 空间与 inode 正常fi# 2.3 文件句柄仅当进程存在时检查if$PROCESS_EXISTS;thenFD_COUNT$(ls/proc/$JENKINS_PID/fd2/dev/null|wc-l)FD_LIMIT$(grepMax open files/proc/$JENKINS_PID/limits2/dev/null|awk{print $4})if[-n$FD_LIMIT][$FD_COUNT-ge$((FD_LIMIT*80/100))];thenecho-e${RED}[致命] 文件句柄使用量接近上限:$FD_COUNT/$FD_LIMIT${NC}FATAL_SIGNAL_FOUNDtrueelseecho[句柄] 正常 ($FD_COUNT/$FD_LIMIT)fifi# 2.4 JVM 崩溃日志echo[检查] JVM 致命错误日志...HS_ERR$(find$JENKINS_HOME/tmp /var/log-namehs_err_pid*-mmin-602/dev/null|head-1)if[-n$HS_ERR];thenecho-e${RED}[致命] 发现 JVM 崩溃日志:$HS_ERR${NC}head-20$HS_ERRFATAL_SIGNAL_FOUNDtrueelseecho[JVM] 未发现 hs_err_pid 文件fi# 奥卡姆剃刀决策点若已发现致命信号可立即提示if$FATAL_SIGNAL_FOUND;thenechoecho-e${YELLOW}★★★ 奥卡姆剃刀结论已捕获致命信号建议直接针对上述发现处理无需继续深挖。★★★${NC}# 【手工检验注释】# - 若是 OOM用 free -h、ps aux --sort-%mem | head 分析内存分布# - 若是磁盘满用 du -sh /var/lib/jenkins/jobs/*/builds/* | sort -rh | head 找出大目录# - 若为 JVM 崩溃检查 hs_err 文件中 Internal Error 和 Stack 段考虑 JDK 版本与插件兼容性# 然后按辩证决策第三步决定立即重启还是继续取证。fiecho# ---------- 3. 辩证决策恢复 vs 深挖 ----------echo-e${GREEN} 第三步辩证决策 —— 恢复与根因的权衡 ${NC}# 尝试简单判断是否处于业务高峰例如当前时间HOUR$(date%H)if[$HOUR-ge9][$HOUR-le18];thenPEAK_TIMEtrueecho[时间] 当前处于业务高峰时段 (9-18点)elsePEAK_TIMEfalseecho[时间] 当前处于低峰时段fi# 【手工检验注释】# 这里需要人工介入决策。脚本仅给出建议# 若为业务高峰且致命信号已明确建议立即执行预案恢复但务必先执行以下命令保存现场# journalctl -u jenkins --since 30 minutes ago /tmp/jenkins_crash_snapshot.log# cp -r /var/lib/jenkins /tmp/jenkins_home_backup_$(date %Y%m%d_%H%M) # 注意磁盘空间# 然后重启服务 systemctl restart jenkins# 若为低峰或致命信号不明确请继续执行本脚本的后续深度分析部分。echoread-p是否继续深度分析(y/n默认 y): CONTINUECONTINUE${CONTINUE:-y}if[$CONTINUE!y];thenecho已跳过深度分析。请根据需要重启服务或人工介入。exit0fi# ---------- 4. 整体论与深度分析 ----------echo-e${GREEN} 第四步整体论深度分析 —— 关联与涌现行为 ${NC}# 4.1 Jenkins 自身日志最近的错误echo[日志] 抓取 Jenkins 服务日志最后$LOG_LINES行...journalctl-ujenkins --no-pager-n$LOG_LINES2/dev/null||\tail-n$LOG_LINES$JENKINS_HOME/../jenkins.log2/dev/null||\echo无法获取 Jenkins 日志请手工检查 /var/log/jenkins/# 4.2 系统资源全景关联 OOM 时刻echoecho[系统] 内存与 Swap 现状free-hechoecho[系统] 当前 CPU 负载与进程 Top 5top-bn1|head-15echoecho[系统] 当前磁盘 I/O 等待iostat-x122/dev/null|tail-20||echoiostat 未安装# 4.3 依赖连通性检查整体论视角echoecho[依赖] 测试关键外部服务连通性...# Git 仓库连通性示例GIT_REPO$(grep-rgit$JENKINS_HOME/jobs-l2/dev/null|head-1)if[-f$GIT_REPO];thenREMOTE_URL$(grep-oP(?url)[^]$GIT_REPO|head-1)if[-n$REMOTE_URL];thentimeout5gitls-remote$REMOTE_URL/dev/null21\echo[Git]$REMOTE_URL可达||\echo-e${RED}[Git]$REMOTE_URL不可达${NC}fielseecho[Git] 未找到仓库配置跳过fi# 检查本地端口占用情况监控系统滥用短连接echoecho[网络] TIME_WAIT 连接数量ss-s|grep-itimewait||echo无 TIME_WAIT 统计# 【手工检验注释】# - 若怀疑某个外部依赖如 Git、Nexus拖慢 Jenkins可用 telnet/tcping 测试延迟。# - 若 TIME_WAIT 数量极高数千考虑优化内核参数或调整监控频率。# - 使用 eBPF 工具进一步分析sudo filetop -C 5 可实时看到哪个进程在写盘最多。echo# ---------- 5. 数据完整性当进程尝试启动但立即退出时必需----------echo-e${GREEN} 第五步数据完整性检查 ${NC}if$PROCESS_EXISTS;thenecho进程尚存跳过数据完整性检查。若要验证请先停止 Jenkins。else# 尝试前台启动并捕获错误只运行5秒用于诊断echo[数据] 尝试前台启动 Jenkins 5 秒以捕获配置错误...sudo-u$JENKINS_USERtimeout5java-jar/usr/share/jenkins/jenkins.war\--httpPort$JENKINS_PORT--webroot/var/cache/jenkins/war\21|tee/tmp/jenkins_foreground.logechoecho[数据] 常见错误检查grep-isaxparse\|xstream\|config.xml/tmp/jenkins_foreground.log\echo-e${RED}发现 XML 配置损坏请恢复备份或检查对应文件${NC}||\echo未发现 XML 解析错误grep-inoclassdeffound\|linkageerror/tmp/jenkins_foreground.log\echo-e${RED}发现插件冲突或类加载错误考虑进入安全模式或移除最近更新的插件${NC}||\echo未发现插件冲突fi# 【手工检验注释】# 若前台启动报错定位到具体文件如 /var/lib/jenkins/jobs/xxx/config.xml 损坏# cp /var/lib/jenkins/jobs/xxx/config.xml /var/lib/jenkins/jobs/xxx/config.xml.bak# 然后尝试用空白配置替换或手动修复 XML。# 若为插件冲突可暂时移动插件 mv /var/lib/jenkins/plugins/xxx.jpi /tmp/echo# ---------- 6. 无为防御展示当前自愈配置 ----------echo-e${GREEN} 第六步无为防御 —— 自愈配置现状 ${NC}echo[cron] 检查磁盘清理任务...crontab-l2/dev/null|grep-ijenkins\|clean\|disk||echo未找到相关 cron 任务建议添加磁盘自动清理echo[systemd] 检查内存限制...ifsystemctlcatjenkins2/dev/null|grep-qMemoryMax\|MemoryHigh;thensystemctlcatjenkins2/dev/null|grep-EMemoryMax|MemoryHighelseecho未设置 MemoryMax/MemoryHigh建议为 Jenkins 配置内存限制以防 OOMfiecho[健康检查] 建议配置 Jenkins 健康检查端点 (如 /login)# 【手工检验注释】# 无为防御的最佳实践# - 添加 cron: 0 3 * * * find /var/lib/jenkins/jobs/*/builds -maxdepth 0 -mtime 7 -exec rm -rf {} \;# - 编辑 /etc/systemd/system/jenkins.service.d/override.conf 添加:# [Service]# MemoryHigh4G# MemoryMax5G# - 使用 systemd 的 ExecStartPre 校验关键 XML:# ExecStartPre/usr/bin/xmllint --noout /var/lib/jenkins/config.xmlechoecho-e${GREEN} 排查脚本执行完毕 ${NC}echo请根据上述输出定位根因。若为致命信号且已执行恢复请将本次日志保存用于事后分析。