Jenkins Execute Shell通过SSH检测远程文件存在时构建失败问题问询
问题排查与修复方案
原有代码核心错误点
- 输出重定向位置错误:你把
2>/dev/null 1>/dev/null单独写为一行,会清空前面echo输出的yes/no内容,且后续$?获取到的是这条空重定向命令的执行状态码,并非文件检测命令的结果 - 状态码逻辑错误:
$?返回的是上一条命令的数字类型退出码(0代表执行成功,非0代表执行失败),不可能等于字符串yes,你的判断条件永远不会触发 - 变量作用域错误:
currentBuild.result是Jenkins本地的流水线变量,写在远程SSH执行的代码块中,远程机器无法识别该变量,配置不会生效 - 退出码传递逻辑缺失:远程SSH会话内执行
exit 1只会终止远程的shell进程,你需要将退出状态回传到Jenkins本地,才能触发构建失败标记 - 文件检测方式不严谨:用
ls判断文件存在容易受别名、通配符匹配等异常情况影响,优先使用test -f命令判断普通文件是否存在
修复后的可用代码
# 执行远程检测,远程脚本的退出码会直接作为ssh命令的返回值 sshpass -p ${ServerNodePw} ssh -T -o UserKnownHostsFile=/dev/null -o StrictHostKeyChecking=no ${ServerNodeUser}@${ServerNodeIP} << 'EOSSH' LOCK_FILE="/Volumes/ServerHD/Users/username/Desktop/JenkinsVMbuild.lock" if [ -f "${LOCK_FILE}" ]; then echo "File found" exit 1 else echo "File not found" exit 0 fi EOSSH # 捕获ssh命令的退出码,即远程检测逻辑的执行结果 SSH_RET=$? if [ ${SSH_RET} -ne 0 ]; then echo "检测到目标机器存在锁文件,终止构建" # 仅Jenkins流水线项目需要下面这行,自由风格项目直接exit 1即可自动标记构建失败 currentBuild.result='FAILURE' exit 1 fi
额外说明
- 远程脚本边界符
EOSSH加了单引号,作用是避免Jenkins本地提前解析远程脚本内的变量,保证所有变量都在目标机器上完成解析 - 不需要额外输出
yes/no做判断,直接通过ssh命令的返回值就能拿到远程检测的结果,逻辑更简洁不容易出错
内容的提问来源于stack exchange,提问作者Brent Ellis
相关产品推荐
相关产品推荐

