我的管道出现间歇性故障,导致我不得不偶尔重新启动作业。 此故障导致的输出字符串是可以预测的。 假设是“构建失败”。 我想仅在原始任务的输出中存在该字符串的情况下使用“retryCountOnTaskFailure:”自动重试该作业。 如果这是更合理的失败,这将阻止作业重试。 我该如何调理?
这使用 Azure Devops 和 *.yaml 脚本。这项工作看起来像:
job: my_job
steps:
- powershell: |
cmake .
retryCountOnTaskFailure: 1
我已经添加了 retryCountOnTaskFailure,如 DevOps 文档中所示,但这将始终重试作业,无论发生什么类型的故障。
到目前为止,恐怕还没有现成的功能可以自动重新运行代理作业,更不用说如何在某些条件下重新运行作业了。据我测试,在构建过程中尝试重新运行当前构建时,我们可能会遇到以下错误。
API当阶段PredictFailure
my_job
中的 A
PowerShell 任务因可预测错误而失败时,它输出一个变量
$(PredictFailure.message)
,其值为 TheBuildHasFailed
。阶段trigger_stageB
A
将评估my_job
的状态,以及输出变量dependencies.my_job.outputs['PredictFailure.message']
的值是否等于TheBuildHasFailed
;一旦评估通过,它将 Invoke REST API
触发当前构建的
B
阶段。
经过一段时间的手动验证后,阶段B
A
中的失败作业。您可以在该时间内拒绝重新运行请求。
variables:
OrgName: ${{ split(variables['System.CollectionUri'], '/')[3] }} # Extract organization name from $(System.CollectionUri) - https://dev.azure.com/MyOrgName
stages:
- stage: A
jobs:
- job: my_job
steps:
- powershell: |
Write-Host "When the step is predictable to fail with the failure TheBuildHasFailed, then output"
Write-Host "##vso[task.setvariable variable=message;isoutput=true]TheBuildHasFailed"
exit 1
name: PredictFailure
- powershell: |
echo $(PredictFailure.message)
displayName: Check output
condition: always()
- job: trigger_stageB
dependsOn: my_job
condition: and(
failed(),
eq(dependencies.my_job.outputs['PredictFailure.message'], 'TheBuildHasFailed')
)
pool: server
steps:
- task: InvokeRESTAPI@1
inputs:
connectionType: 'connectedServiceName'
serviceConnection: 'AzureDevOpsServices'
method: 'PATCH'
headers: |
{
"Content-Type":"application/json",
"Authorization": "Bearer $(System.AccessToken)"
}
body: |
{
"state":2,
"forceRetryAllJobs":true,
"retryDependencies":true
}
urlSuffix: '$(OrgName)/$(System.TeamProjectId)/_apis/build/builds/$(Build.BuildId)/stages/B?api-version=7.1'
waitForCompletion: 'false'
- stage: B
trigger: manual
pool: server
jobs:
- job: rerun_stageA
steps:
- task: ManualValidation@1
inputs:
onTimeout: 'resume'
timeoutInMinutes: 1 # Wait for 1 minute before rerun; the rerun request can be rejected manualy within the timespan;
- task: InvokeRESTAPI@1
inputs:
connectionType: 'connectedServiceName'
serviceConnection: 'AzureDevOpsServices'
method: 'PATCH'
headers: |
{
"Content-Type":"application/json",
"Authorization": "Bearer $(System.AccessToken)"
}
body: |
{
"state": 1,
"forceRetryAllJobs": "false",
"retryDependencies": "true"
}
urlSuffix: '/$(OrgName)/$(System.TeamProjectId)/_apis/build/builds/$(Build.BuildId)/stages/A?api-version=7.1'
waitForCompletion: 'false'