管道运行故障排除
Azure DevOps Services | Azure DevOps Server 2022 - Azure DevOps Server 2019
如果管道运行无法完成,可以使用管道运行摘要页面提供的诊断信息和日志来帮助排查问题。
查看日志
选择错误消息来查看未能完成的任务的日志。
将显示日志页面,其中的错误已选定。 在此示例中,cmd-line
任务中存在错误,其中的 echo
命令输入为 ech
。
可以通过选择“查看原始日志”来查看任务的原始日志,并且可以使用“查找”在日志中进行搜索。
扫描失败任务的日志,以获取错误信息以及有关任务失败原因的线索。 默认情况下,不详细的日志由管道运行生成。 如果默认日志未指明问题的原因,可以通过配置详细日志来获取更多信息。
“错误分析”页
使用“错误分析”页可以获得问题排查帮助。 将鼠标移到错误信息行上,然后选择“查看分析”图标。
对于自托管代理,请选择“查看代理”(对于 Microsoft 托管代理,请选择“关于托管代理映像”)以查看有关用于运行管道的代理的详细信息,然后选择“查看日志”以查看管道运行日志。
选择“运行时详细信息”下方的任务的名称以查看有关该任务的信息。
在此示例中,可以看到 Script
的 Value
中存在错误。 选择“关于此任务”以查看任务的文档。
如果从管道运行摘要页面看不到问题,或在浏览日志时看不到问题,请查看下面的常见问题部分,并参阅查看日志以诊断管道问题,了解如何下载完整日志,其中包含其他诊断信息。
常见问题
- 作业超时
- 下载代码时出现问题
- 我的管道在命令行步骤(如 MSBUILD)中失败
- 正在使用的文件或文件夹错误
- MSBuild 故障断断续续或变化无常
- 进程停止响应
- 多个平台的行尾
- 变量追加了 '(单引号)
- 与服务连接相关问题
- 管道停止从代理接收信息
失败管道运行的任务见解
Azure DevOps 提供了失败管道运行的任务见解设置,启用该设置后,它会提供生成失败的弹出通知,并提供用于查看报告的链接。
若要配置此设置,请导航到预览功能,找到失败管道运行的任务见解,然后选择所需的设置。
作业超时
管道可能长时间运行,然后由于作业超时而失败。作业超时很大程度上取决于所使用的代理。 对于专用存储库,免费 Microsoft 托管代理的最大超时时间为每个作业 60 分钟,对于公共存储库,该时间为 360 分钟。 若要增加作业的最大超时时间,可以选择以下任一选项。
- 购买 Microsoft 托管代理,无论使用的是什么存储库,该代理都将为所有作业提供 360 分钟的时间
- 使用自托管代理来排除由于代理而导致的任何超时问题
详细了解作业的超时。
注意
如果 Microsoft 托管代理作业超时,请确保你没有指定一个小于作业最大超时时间的管道超时时间。 若要检查,请参阅超时。
下载代码时出现问题
我的管道在签出步骤中失败
如果对组织中的 Azure Repos Git 存储库使用 checkout
步骤,而该存储库与管道在不同的项目中,请确保禁用“将作业授权范围限制为当前项目”设置,或按照范围内的生成标识中的步骤操作,以确保管道有权访问存储库。
当管道由于作业授权范围有限而无法访问存储库时,你将收到错误 Git fetch failed with exit code 128
,并且日志将包含类似于 Remote: TF401019: The Git repository with name or identifier <your repo name> does not exist or you do not have permissions for the operation you are attempting.
的条目
如果管道立即发生故障并显示 Could not find a project that corresponds with the repository
,请确保 checkout
步骤或存储库资源声明中的项目和存储库名称正确无误。
Team Foundation 版本控制 (TFVC) 问题
获取的源未下载某些文件
这可能通过来自 tf get
命令的日志中的“所有文件已最新”消息来指明。 验证内置服务标识是否有权下载源。 项目集合生成服务标识或项目生成服务标识都需要权限才能下载源,具体取决于生成管道的“常规”选项卡上选定的授权范围。 在版本控制 Web UI 中,可以在文件夹层次结构的任何级别浏览项目文件,并检查安全设置。
通过 Team Foundation 代理获取源
配置代理以通过 Team Foundation 代理获取源的最简单方法是设置环境变量 TFSPROXY
,让它为代理的用户运行指向 TFVC 代理服务器。
Windows:
set TFSPROXY=http://tfvcproxy:8081
setx TFSPROXY=http://tfvcproxy:8081 // If the agent service is running as NETWORKSERVICE or any service account you can't easily set user level environment variable
macOS/Linux:
export TFSPROXY=http://tfvcproxy:8081
我的管道在命令行步骤(如 MSBUILD)上失败
这有助于缩小调查范围,判断生成或发布失败原因是与 Azure Pipelines 还是 TFS 产品问题(代理或任务)有关。 生成和发布失败也可能由外部命令导致。
检查日志,看看失败的任务所执行的确切命令行。 尝试从命令行以本地方式运行命令可能会重现问题。 从自己的计算机以本地方式运行命令和/或登录到计算机并作为服务帐户运行命令,可能会有帮助。
例如,问题是否发生在生成管道的 MSBuild 部分(例如,是否使用了 MSBuild 或 Visual Studio 生成任务)? 如果是这样,请尝试在本地计算机上使用相同的参数运行相同的 MSBuild 命令。 如果可以在本地计算机上重现问题,下一步就是调查 MSBuild 问题。
文件布局
在托管代理上,某个生成所需的工具、库、标头和其他内容的位置可能与本地计算机不同。 如果生成因为找不到其中一个文件而失败,则可以使用以下脚本检查代理上的布局。 这可以帮助你跟踪缺失文件。
在一个临时位置创建新的 YAML 管道(例如,为故障排除而创建的新存储库)。
按照编写的内容,该脚本将搜索路径上的目录。
可以选择编辑 SEARCH_PATH=
行以搜索其他位置。
# Script for Linux and macOS
pool: { vmImage: ubuntu-latest } # or whatever pool you use
steps:
- checkout: none
- bash: |
SEARCH_PATH=$PATH # or any colon-delimited list of paths
IFS=':' read -r -a PathDirs <<< "$SEARCH_PATH"
echo "##[debug] Found directories"
for element in "${PathDirs[@]}"; do
echo "$element"
done;
echo;
echo;
echo "##[debug] Found files"
for element in "${PathDirs[@]}"; do
find "$element" -type f
done
# Script for Windows
pool: { vmImage: windows-2019 } # or whatever pool you use
steps:
- checkout: none
- powershell: |
$SEARCH_PATH=$Env:Path
Write-Host "##[debug] Found directories"
ForEach ($Dir in $SEARCH_PATH -split ";") {
Write-Host "$Dir"
}
Write-Host ""
Write-Host ""
Write-Host "##[debug] Found files"
ForEach ($Dir in $SEARCH_PATH -split ";") {
Get-ChildItem $Dir -File -ErrorAction Continue | ForEach-Object -Process {
Write-Host $_.FullName
}
}
本地命令提示符和代理之间存在差异
请记住,在本地计算机上执行命令以及在代理上运行生成或发布时,一些差异是有效的。 如果代理配置为在 Linux、macOS 或 Windows 上作为服务运行,则它不会在交互式登录会话中运行。 如果没有交互式登录会话,则存在 UI 交互和其他限制。
正在使用的文件或文件夹错误
File or folder in use
错误通常由如下错误消息指明:
Access to the path [...] is denied.
The process cannot access the file [...] because it is being used by another process.
Access is denied.
Can't move [...] to [...]
疑难解答步骤:
检测正在使用的文件和文件夹
在 Windows 上,进程监视器等工具可用于捕获特定目录下的文件事件的跟踪。 或者,对于实时快照,可以使用进程资源管理器或句柄等工具。
防病毒排除
扫描文件的防病毒软件可能会导致在生成或发布期间出现“文件或文件夹正在使用”的错误。 为代理目录和已配置的“工作文件夹”添加防病毒排除,可能有助于将防病毒软件识别为干扰进程。
MSBuild 和 /nodeReuse:false
如果在生成期间调用 MSBuild,请确保传递参数 /nodeReuse:false
(缩写形式为 /nr:false
)。 否则,在生成完成后,MSBuild 进程将保持运行状态。 该进程会保留一段时间,以便进行潜在的后续生成。
MSBuild 的这项功能可能会干扰删除或移动目录的尝试,这是因为与 MSBuild 进程的工作目录发生冲突。
MSBuild 和 Visual Studio 生成任务已将 /nr:false
添加到传递给 MSBuild 的参数。 但是,如果你从自己的脚本调用 MSBuild,则需要指定参数。
MSBuild 和 /maxcpucount:[n]
默认情况下,生成任务(如 MSBuild 和 Visual Studio 生成)使用 /m
开关运行 MSBuild。 在某些情况下,这可能会导致问题,例如多个进程文件访问问题。
尝试将 /m:1
参数添加到生成任务,以强制 MSBuild 一次只运行一个进程。
利用 MSBuild 的并发进程功能时,可能会导致“文件正在使用”问题。 不指定参数 /maxcpucount:[n]
(缩写形式为 /m:[n]
)的情况会指示 MSBuild 仅使用单个进程。 如果使用 MSBuild 或 Visual Studio 生成任务,可能需要指定“/m:1”来替代默认添加的“/m”参数。
MSBuild 故障断断续续或变化无常
如果遇到间歇性故障或 MSBuild 不一致的故障,请尝试指示 MSBuild 只使用单一进程。 间歇性错误或不一致的错误可能指示目标配置与 MSBuild 的并发进程功能不兼容。 请参阅 MSBuild 和 /maxcpucount:[n]。
进程停止响应
进程停止响应的原因和故障排除步骤:
正在等待输入
停止响应的进程可能指示进程正在等待输入。
从交互式登录会话的命令行运行代理,可能有助于确定进程是否以对话方式提示输入。
将代理作为服务运行可能有助于避免程序提示输入的情况。 例如,在 .NET 中,程序可能依赖于 System.Environment.UserInteractive 布尔值来确定是否进行提示。 当代理作为 Windows 服务运行时,该值为 false。
进程转储
分析进程的转储有助于确定死锁进程正在等待的内容。
WiX 项目
在启用自定义 MSBuild 记录器时生成 WiX 项目可能会导致 WiX 死锁等待输出流。 添加额外的 MSBuild 参数 /p:RunWixToolsOutOfProc=true
将解决此问题。
多个平台的行尾
在多个平台上运行管道时,有时可能会遇到具有不同行尾的问题。 在过去,Linux 和 macOS 使用了换行符 (LF),而 Windows 使用了回车加上换行符 (CRLF)。 Git 尝试在存储库中自动使行以 LF 结尾,但在 Windows 上的工作目录中以 CRLF 结尾,通过这种方式来弥补差异。
大多数 Windows 工具都可以仅以 LF 结尾,这种自动行为可能会带来更多的问题,而不是很好地解决问题。
如果遇到行尾相关的问题,建议将 Git 配置为在任何位置都首选 LF。
为此,请将 .gitattributes
文件添加到存储库的根目录中。
在该文件中,添加以下行:
* text eol=lf
变量追加了 '(单引号)
如果管道包含使用 ##vso
命令设置变量的 Bash 脚本,则可能会看到一个额外的 '
追加到所设置的变量的值。
发生这种情况是因为与 set -x
进行了交互。
解决方法是在设置变量之前暂时禁用 set -x
。
用于执行此操作的 Bash 语法为 set +x
。
set +x
echo ##vso[task.setvariable variable=MY_VAR]my_value
set -x
为何发生这种情况?
许多 Bash 脚本都包含 set -x
命令来辅助调试。
Bash 将准确跟踪已执行的命令,并将其回显到 stdout。
这将导致代理看到 ##vso
命令两次,第二次,Bash 会将 '
字符添加到末尾。
例如,来看看以下管道:
steps:
- bash: |
set -x
echo ##vso[task.setvariable variable=MY_VAR]my_value
在 stdout 上,代理将看到两行:
##vso[task.setvariable variable=MY_VAR]my_value
+ echo '##vso[task.setvariable variable=MY_VAR]my_value'
当代理看到第一行时,MY_VAR
将设置为正确的值“my_value”。
但是,当代理看到第二行时,它将处理追加到行尾的所有内容。
MY_VAR
将设置为“my_value'”。
脚本执行时没有为 Python 应用程序安装库
部署 Python 应用程序时,在某些情况下,CI/CD 管道将运行且代码部署成功,但负责安装所有依赖项库的 requirements.txt 文件不会执行。
若要安装依赖项,请在应用服务部署任务中使用部署后脚本。 下面的示例展示了必须在部署后脚本中使用的命令。 可以为实际场景更新脚本。
D:\home\python364x64\python.exe -m pip install -r requirements.txt
与服务连接相关问题
若要排查与服务连接相关的问题,请参阅服务连接故障排除。
管道停止从代理接收信息
如果管道失败并显示类似”We stopped hearing from agent <agent name>. Verify the agent machine is running and has a healthy network connection.
“的消息,则请检查代理的资源利用率,以查看代理计算机是否已耗尽资源。 从 Sprint 228 开始,Azure Pipelines 日志包含每个步骤的资源利用率指标。
在使用 Azure DevOps Services 时,启用 verbose logs 可以查看日志中的资源利用率,包括磁盘使用情况、内存使用情况和 CPU 利用率。 在管道完成后,请搜索日志以查找每个步骤的 Agent environment resources
条目。
2024-02-28T17:41:15.1315148Z ##[debug]Agent environment resources - Disk: D:\ Available 12342.00 MB out of 14333.00 MB, Memory: Used 1907.00 MB out of 7167.00 MB, CPU: Usage 17.23%
有关捕获其他资源利用率日志的信息,请参阅捕获资源利用率详细信息。
允许存储资源管理器通过 Azure Pipelines 将静态内容(如 .css 和 .js)从 Azure DevOps 部署到静态网站
在此场景中,可以使用 Azure 文件复制任务将内容上传到网站。 可以使用上传内容中所述的任何工具将内容上传到 Web 容器。