GitLab CI任务存在错误却仍显示成功的排查与修复
GitLab CI流水线任务出错却标记成功的问题排查与修复
问题描述
我有一个将软件包推送到服务器的GitLab CI流水线,日志显示aptly repo add无法找到目标deb文件,但任务仍被标记为成功。相关日志、CI任务配置和脚本如下:
部分错误日志
ECHO sudo aptly repo add stable abc.deb Loading packages... [!] Unable to process abc.deb: stat abc.deb: no such file or directory [!] Some files were skipped due to errors: abc.deb ... Job succeeded
CI任务配置(Edit 1)
deploy-on: stage: deploy image: ubuntu:20.04 before_script: - apt-get update - apt-get install sshpass -y - apt-get install aptly -y - apt-get install sudo -y script: - pOSOP=publisher - unstableOrStable=stable - chmod +x ./pushToServer.sh - ./publishToServer.sh
pushToServer.sh脚本(Edit 1)
#!/bin/bash cat build.env DebFileNameW=$(cat build.env | grep DebFileNameW | cut -d = -f2) echo "DebFileNameW=" $DebFileNameW sshpass -p pass ssh -oStrictHostKeyChecking=no $pOSOP ' echo "ECHO mkdir -p /home/packages/" mkdir -p /home/packages/ exit ' sshpass -p pass scp -oStrictHostKeyChecking=no build/$DebFileNameW.deb $pOSOP:/home/packages/ echo "making time" file_name=$DebFileNameW current_time=$(date "+%Y.%m.%d-%H.%M.%S") sshpass -p pass ssh -t -oStrictHostKeyChecking=no $pOSOP ' echo "doing cd" cd /home/packages echo "ECHO sudo aptly repo add '$unstableOrStable' '$file_name'.deb" sudo aptly repo add '$unstableOrStable' '$file_name'.deb '
尝试的无效修复(Edit 2)
在SSH会话内添加退出码判断,但捕获到的始终是0:
retVal=$? echo "ECHOO exit status" $retVal if [ $retVal -ne 0 ]; then echo "<meaningful message>" exit $retVal fi
日志显示ECHOO exit status 0,任务依然成功。
原因分析
- Aptly默认行为:
aptly repo add在遇到部分文件处理失败时,默认返回退出码0——它认为只是跳过错误文件,整体操作未完全失败,不会主动终止。 - SSH会话的退出码隔离:在SSH会话内部判断退出码,拿到的是SSH会话自身的结束状态(只要会话正常关闭就返回0),而非远程执行的
aptly命令的真实退出码。 - GitLab CI的判断逻辑:GitLab仅依据脚本最后一条命令的退出码判断任务状态,只要是0就标记为成功,不会解析日志中的错误信息。
解决思路
1. 强制Aptly在出错时返回非0退出码
给aptly repo add添加-strict参数,这样只要有任何文件处理失败,Aptly就会立刻终止并返回非0退出码:
sudo aptly repo add -strict '$unstableOrStable' '$file_name'.deb
2. 让SSH会话返回远程命令的真实退出码
在远程SSH会话中开启set -e,确保任何命令出错时立刻终止会话,让SSH返回该错误码:
sshpass -p pass ssh -t -oStrictHostKeyChecking=no $pOSOP ' set -e echo "doing cd" cd /home/packages echo "ECHO sudo aptly repo add -strict '$unstableOrStable' '$file_name'.deb" sudo aptly repo add -strict '$unstableOrStable' '$file_name'.deb '
3. 在本地脚本中检查SSH命令的退出码
执行完SSH命令后,立刻在本地脚本中判断退出码,非0则终止任务:
# 执行远程aptly命令 sshpass -p pass ssh -t -oStrictHostKeyChecking=no $pOSOP ' set -e cd /home/packages sudo aptly repo add -strict '$unstableOrStable' '$file_name'.deb ' # 检查SSH命令的退出码 if [ $? -ne 0 ]; then echo "Aptly添加软件包失败,任务终止" exit 1 fi
4. 额外:提前检查SCP上传是否成功
如果SCP上传deb文件失败(比如本地文件不存在),后续aptly必然出错,所以要在SCP后添加退出码检查:
sshpass -p pass scp -oStrictHostKeyChecking=no build/$DebFileNameW.deb $pOSOP:/home/packages/ if [ $? -ne 0 ]; then echo "上传deb文件到服务器失败,任务终止" exit 1 fi
验证效果
修改完成后,当aptly无法找到deb文件时,会返回非0退出码,SSH会话将该码传回本地脚本,脚本执行exit 1,GitLab CI会正确标记任务为失败。
内容的提问来源于stack exchange,提问作者Thor
相关产品推荐
相关产品推荐

