症状:Mac 重启后流水线提示没有可用 Runner,或 Runner 页面显示离线。
最快解法:先让运行 Runner 的 macOS 账号登录图形桌面,再检查用户级 LaunchAgent、服务状态和 GitLab 连接;不要先把自动登录当成通用修复。

适合你:数字游民或远程开发者,重启远程 Mac 后需要恢复项目构建;独立 iOS 开发者,正在确认 Runner 是否依赖用户会话;小型远程团队,想评估持续维护自管 Runner 的责任与恢复流程。

先判定故障发生在调度端还是 Mac 主机

Mac 重启后,GitLab CI/CD 为什么可能找不到 Runner? 常见原因不止 Runner 服务未启动。还可能是 Runner 已离线、任务标签不匹配、Runner 暂停,或它没有被分配给当前项目。先看项目的 Runner 页面和具体任务状态,再决定是否登录 Mac 排查。

在 GitLab 项目中打开 Runner 列表,记录该 Runner 的在线状态、标签、暂停状态和适用范围。再打开卡住的流水线任务,核对 .gitlab-ci.yml 中的 tags。一个在线 Runner 如果缺少任务要求的任意标签,同样不会接手任务;未授权给项目的 Runner 也不能因为主机正常就自动参与调度。GitLab 文档说明 Runner 标签如何匹配任务。

如果页面明确显示离线,排查主机;如果 Runner 在线、任务却一直等待,优先检查标签、项目范围和是否允许无标签任务。GitLab 的 Runner API 也区分在线、离线、暂停等状态,可作为页面状态之外的核对方式。Runner API 状态字段说明。

⚠️ 不要在同一轮排查里同时改标签、重新注册 Runner、重装 Xcode。一次只改一个变量,保留改动前后的页面状态和作业日志,否则很难判断真正原因。

核对 LaunchAgent 与运行账号的登录会话

如何确认 macOS Runner 是否已启动? 在 Runner 原本使用的 macOS 账号下打开终端,先运行:

gitlab-runner status
gitlab-runner list
gitlab-runner verify

status 检查本机服务状态,list 查看本地配置中的 Runner,verify 检查已注册 Runner 是否能连接 GitLab。注意,连接验证成功并不等于服务正在运行,也不等于 GitLab 已向它派发任务;这几个命令回答的是不同问题。GitLab Runner 命令文档对这些命令的作用有明确区分。

macOS 上,GitLab Runner 支持的服务模式是用户级 LaunchAgent,不是系统级 LaunchDaemon。官方安装说明给出的 plist 路径是 ~/Library/LaunchAgents/gitlab-runner.plist。LaunchAgent 随对应用户登录启动,并在该用户退出登录时停止;LaunchDaemon 虽然是系统级启动方式,却不能替代 Runner 所需的用户会话。iOS 模拟器和签名流程也可能需要用户会话、钥匙串或图形环境。GitLab macOS 安装说明。

在本机再核对 plist 是否存在、运行账号是否正确,并查看启动错误:

ls -l ~/Library/LaunchAgents/gitlab-runner.plist
launchctl list | grep gitlab-runner
gitlab-runner status

如果你通过 SSH 登录后才运行 gitlab-runner start,出现 Could not find domain for 等错误,不要据此断定主机上的 Runner 已坏。GitLab 的 macOS 故障排查说明指出,安装和启动服务应从本地图形会话中的终端操作;LaunchAgent 需要可用的图形登录会话来加载。先通过远程桌面或主机本地登录对应账号,再执行服务操作。

断开 SSH 后 Runner 会不会离线? 不能只看 SSH 断开这一件事下结论。SSH 连接结束,不等同于 macOS 用户注销;用户会话是否仍在、LaunchAgent 是否仍运行,才是要核对的证据。实际处理时比较断开前后的 gitlab-runner status、GitLab 页面状态和主机日志,不要把断开 SSH、注销和重启当成同一种操作。

在线但不接单时,沿着标签与连接继续查

如果服务状态正常,但 GitLab 页面仍显示离线,运行 gitlab-runner verify 并检查网络出口、代理、防火墙和 Runner 配置中的 GitLab 地址。验证失败时,先处理连接或认证问题;不要急着重新注册。重新注册会改动本地配置,重复操作还可能留下难以辨认的 Runner 条目。GitLab 的 macOS 安装文档也列出了无法连接 GitLab、服务启动失败等排查方向。

如果 verify 成功、页面在线但任务不接单,回到调度端核对项目授权和标签。任务列出的标签必须全部符合 Runner 的标签配置;Runner 只接带标签任务时,无标签任务也不会被匹配。按项目、组或实例的范围注册 Runner,也会影响哪些项目能使用它。

在线状态是否代表 iOS 构建已经恢复? 不代表。你要分别确认 Runner 能连接 GitLab、任务实际被领取、作业执行成功,以及 Xcode 构建通过。任何一个环节失败,都不能用“页面显示在线”替代完整验收。

观察到的现象 优先检查 下一步判断
项目页面显示 Runner 离线 用户是否登录、LaunchAgent 是否启动、verify 是否成功 登录图形会话并检查服务与网络
Runner 在线,任务仍等待 项目授权、Runner 与任务标签、是否接收无标签任务 修正调度条件,不先重装主机环境
任务已领取,但作业报错 用户权限、作业脚本、环境变量和日志 按首条实际错误定位执行环境
作业启动后 Xcode 命令失败 Xcode 是否存在、活跃开发者目录与所需组件 修正工具链后重跑构建

检查 Xcode 工具链,不要把构建失败误判为离线

Runner 已接单,作业却在 xcodebuild、模拟器或签名步骤失败,说明排查已经进入构建环境。先在 Runner 所用账号下执行:

whoami
xcode-select --print-path
xcodebuild -version

确认作业执行账号和预期一致,开发者目录指向实际安装的 Xcode。Apple 文档说明,xcode-select 用于查看或切换当前命令行工具使用的开发者目录;安装或升级后路径不匹配,构建命令可能找不到对应工具。Apple 的 Xcode 命令行工具安装说明。

若项目依赖 Xcode 附加组件或模拟器运行时,按项目所需检查是否已经安装;不要把单独的 Command Line Tools 当作完整 Xcode 环境。Apple 文档指出,xcodebuild 等命令随 Xcode 提供,而附加平台组件可通过 Xcode 工具安装。Apple 的 Xcode 附加组件说明。

拿一条失败作业的完整日志对照检查:它是否在 gitlab-runner 启动前就失败,是否能检出代码,是否能找到 Xcode,是否卡在签名或模拟器环节。这样才能把 Runner 服务在线、GitLab 调度成功、作业成功执行和 Xcode 构建通过分开判断。

评估自动登录与其他恢复方案的代价

GitLab 的 macOS 安装说明提出,为了让 Runner 在重启后可用,可以开启自动登录;其原因是 Runner 依赖用户会话。这个建议有明确边界:它不是所有托管 Mac 或所有安全策略下都适用的保证。启用前,先确定 Runner 账号可访问哪些代码、凭据、钥匙串和项目资源,再评估远程主机的控制台访问权限。

自动登录会改变主机的登录边界。Apple 明确提醒,启用后,任何能重启 Mac 的人都可能进入自动登录账号;不要让管理员账号自动登录。Apple 也说明,开启 FileVault 时自动登录不可用。因此,如果安全策略要求 FileVault 或重启后必须人工认证,不能把自动登录当作可随手开启的恢复开关。Apple 自动登录说明。

方案 恢复条件 优点 主要代价与适用判断
用户登录后由 LaunchAgent 启动 你能及时登录对应 macOS 账号 保留登录边界,符合用户级服务模式 需要人工恢复;适合可接受短暂停顿的流程
启用自动登录 账号和设备策略允许,且可接受物理访问风险 重启后可尝试恢复用户会话与 Runner 降低主机登录门槛;先评估敏感凭据与远程访问控制
备用构建路径 你已提前准备另一条经过验证的构建流程 主机故障时不必把恢复押在单一 Runner 上 需要维护并验证备用环境;适合交付不能等待人工登录的团队

做一次重启演练,再决定是否继续自管

旅途中最容易漏掉的不是“Runner 能不能启动”,而是没人能及时登录、项目凭据留在主机、重启后 Xcode 环境状态不明。用一次计划内演练确认整条恢复链路:

  1. 先记录 GitLab 项目中的 Runner 状态、标签、适用项目范围,以及当前能够成功的构建任务。
  2. 确认本机运行账号、LaunchAgent plist 路径和 gitlab-runner status 结果;保存一份不含敏感令牌的排查记录。
  3. 按你实际要依赖的方式重启 Mac。若生产方案依赖人工登录,就不要用自动登录的演练结果代替。
  4. 登录原运行账号后检查 LaunchAgent 和服务状态,再运行 gitlab-runner verify,观察 GitLab 页面是否恢复在线。
  5. 触发一条真实项目流水线,确认 Runner 接单、作业执行和 Xcode 构建均成功;失败时保留首条错误和对应日志。
  6. 再单独验证注销与断开 SSH 的影响。分别记录结果,不要把其中一项推断成其他场景的表现。

GitLab 的 macOS Runner 配置指南提供安装、注册和作业准备步骤;按该流程搭好之后,仍要用你自己的项目完成上述重启验收,才能证明真实工作负载可恢复。

提醒:gitlab-runner verify 只验证注册 Runner 的连接能力,不替你证明它正在作为服务运行,也不替你证明项目任务能通过。验收记录里要分别写明“服务已启动”“GitLab 可见”“任务已接单”“构建通过”。

根据演练结果做决定:如果图形会话可控、LaunchAgent 稳定启动,且你接受人工登录恢复,可以继续自管;如果业务要求重启后无人值守接单,先评估自动登录风险与主机访问控制,再决定是否调整;如果安全策略不允许自动登录、又不能容忍等待人工介入,就应准备另一条已验证的构建路径,而不是把 LaunchDaemon 当作受支持的替代模式。

如果你确认项目需要持续可访问的 macOS 构建环境,却不想把全部恢复工作都压在自己维护的主机上,可以先了解远程 Mac 的接入与使用方式,再按项目的会话、凭据与重启验收要求判断是否适合。自管 Mac 的优势是环境控制更直接,但你要负责登录会话、服务恢复、工具链和备用方案;临时或阶段性需要远程 macOS 时,也可以查看 MACCOME 的远程 Mac 方案入口,确认使用方式后再决定是否租用。