維護 OpenClaw 分叉或外掛 的團隊,在 2026 年往往同時面對兩條線:上游 OpenClaw CI 裡的 macos-node、macos-swift 與 checks-node-compat-node22 需要真 macOS;而 GitHub 託管 macOS 分鐘費與佇列又推高成本。本文專注在遠端獨享 Mac 上自建 GitHub Actions Runner,用 macOS 標籤池 承接 OpenClaw 原生 lane,並以唯讀 Webhook + Lobster 多步工作流做失敗 triage——不寫 Gateway 18789 安裝、不做六地節點橫評(節點與 TCO 見 Runner 節點與 TCO 文)。套餐見 定價方案,美東/美西公開結帳見 美東結帳、美西結帳,Runner 運維見 幫助中心。
一、託管 macOS Runner vs 遠端 Mac 自建:OpenClaw CI 場景下的決策表
根據 OpenClaw CI 文件,macos-node 在變更觸及 macOS 相關原始碼時執行 TypeScript 測試;macos-swift 負責 Swift lint/建置/測試;手動 workflow_dispatch 會繞過智慧 scope、拉起完整圖(含 Node 22 相容 lane)。官方倉庫預設走 Blacksmith macos-latest 族 Runner,fork 維護者若無法穩定占用上游佇列,就需要自己的 macOS 標籤池。
GitHub 託管 macOS 按分鐘計費,適合低頻 PR;自建則在遠端 M4 上換「固定席位 + 持久 node_modules / DerivedData」,更適合日更 main、外掛契約分片、以及要對齊上游 pnpm check 本地等價指令的團隊。對比六地節點與日租—月租算例請讀 六地 Runner TCO 文,本篇只回答「如何對接 OpenClaw lane」。常駐 Agent/Gateway 部署分工見 OpenClaw 遠端 Mac 實操文(一句:Gateway 管對話與工具面,CI Runner 管編譯與測試)。
| 路徑 | OpenClaw CI 適配 | 主要代價 |
|---|---|---|
GitHub 託管 macos-latest |
零運維跑上游 workflow;fork 難保證與官方同佇列/快取。 | 分鐘費;macos-swift 冷啟動慢;高峰排隊。 |
| 遠端 Mac 自建 Runner | 用 label 映射 macos-node / macos-swift;可固定 Node 22、pnpm store。 |
需維護 Runner 升級、磁碟與併發互斥。 |
| 僅 Linux 託管 + 跳過 macOS lane | 適合純文件/Node 改動;不能替代 Swift/macOS 測試。 | 合併前仍需手動或定時跑 macOS 全量。 |
workflow_dispatch 全量 CI,或 fork 上 macos-node 經常排隊超過 15 分鐘,優先規劃至少一台帶 openclaw-macos-node 標籤的自建機,而不是繼續疊託管分鐘。外掛維護者還可把「託管分鐘費 + 人工盯失敗」與「一台 M4 月租」做 90 天對比,通常在全量 dispatch 場景下更容易回本。二、環境清單:Xcode CLT、Node 22 與 CI 使用者隔離
OpenClaw 上游在 Linux 上跑大部分 Node shard,但 macos-node 與 checks-node-compat-node22 明確要求 Node 22(見 CI 文件中的 compat lane 與本地 pnpm check 等價指令)。在自建 Runner 上建議:
- Xcode Command Line Tools 與目標 Xcode 小版本與團隊凍結策略一致;Swift lane 需完整 Xcode,而非僅 CLT。
- Node 22.x 用
fnm/mise固定,並在~/.zprofile對 CI 使用者生效;workflow 內仍建議actions/setup-node雙保險。 - pnpm 版本與上游
packageManager欄位對齊;快取目錄放在 CI 使用者家目錄,避免與個人開發混用。 - 專用 Unix 使用者(如
runner)安裝actions-runner,不要用日常 Apple ID 或含聊天/瀏覽器金鑰的同一使用者跑 job。 - 資源上限:用
ulimit、Activity Monitor 或memory_pressure觀察;24GB 機型再考慮並行第二 job。
xcode-select -p指向預期 Xcode;xcodebuild -version與文件一致。node -v為 v22.x;pnpm -v與倉庫鎖檔匹配。- CI 使用者可無密碼執行 Runner 服務(
launchd),SSH 斷開仍存活。 - 磁碟剩餘 > 25%(Swift DerivedData + pnpm store 增長快)。
- 倉庫 Secrets 僅注入必要 PAT,推理/Webhook 金鑰與簽章憑證分庫分 Secret。
Apple 平台 API 與簽章行為以 Apple Developer Documentation 為準;Node 版本政策見 nodejs.org。
三、Runner 註冊與 macOS 標籤池(HowTo)
按 GitHub 官方文件 在遠端 Mac 註冊 Runner。對 OpenClaw fork,建議把上游 job 的 runs-on 映射到自建標籤,而不是複用模糊的 self-hosted。
# 在 ~/actions-runner 目錄 ./config.sh --url https://github.com/YOUR_ORG/YOUR_FORK \ --token YOUR_REGISTRATION_TOKEN \ --labels self-hosted,macOS,ARM64,openclaw-macos-node,openclaw-m4-16 \ --name nuv-openclaw-macos-node-01 sudo ./svc.sh install sudo ./svc.sh start
標籤池建議(按 lane 拆分):
openclaw-macos-node— 對應上游macos-node(TypeScript/Vitest macOS 路徑)。openclaw-macos-swift— 對應macos-swift;CPU/記憶體占用更高,勿與 node lane 預設並行在同一台 16GB 機。openclaw-node22— 可選,用於手動 dispatch 的 Node 22 compat 或本地pnpm check冒煙。openclaw-m4-16/openclaw-m4-24— 硬體檔位,便於 workflow 裡做矩陣或容量規劃。
jobs:
macos-node:
runs-on: [self-hosted, macOS, openclaw-macos-node]
steps:
- uses: actions/checkout@v4
- uses: actions/setup-node@v4
with:
node-version: '22'
cache: 'pnpm'
- run: pnpm install --frozen-lockfile
- run: pnpm test --filter macos-relevant
簽章、notarization 等副作用步驟請加 concurrency: { group: codesign-macos, cancel-in-progress: false },避免兩把鑰匙串同時解鎖。更多 SSH/Runner 守護說明見 幫助中心。
四、對接 OpenClaw CI / dispatch 與唯讀 Webhook
上游 CI 在 push/PR 時由 preflight 決定 lane;你可在 fork 中保留該邏輯,僅把 macOS job 的 runs-on 改到自建池。需要全量驗證時,用官方支援的手動 dispatch(文件範例):
gh workflow run ci.yml --ref main gh workflow run ci.yml --ref main -f target_ref=your-branch -f include_android=true
唯讀 Webhook 推理層(推薦分階段):在 CI 失敗 triage 場景,宜先訂閱唯讀事件(如 workflow_run.completed、check_run.completed、workflow_job.completed),把 payload 中繼資料(倉庫、分支、結論、URL)送入閘道或輕量接收端,不要在第一階段申請 Contents 寫權限或自動 merge。驗簽通過後,由 Agent 拉取公開日誌連結或已授權的 Actions API 唯讀範圍做摘要;確認穩定後再擴權(評論 PR、打 label 等)。
| 階段 | Webhook / 權限 | 用途 |
|---|---|---|
| Phase 0 | 唯讀 + workflow_run / check_run |
失敗通知、排隊監控、Lobster triage 輸入。 |
| Phase 1 | 增加 Actions 日誌唯讀 PAT | 拉取 job 日誌片段、關聯 macos-node 失敗 shard。 |
| Phase 2 | 受控寫(issue comment、label) | 自動打 ci-failure、@值班;需審批策略。 |
五、M4 16GB / 24GB 併發簡表(單機標籤池)
以下為OpenClaw macOS lane 的務實併發建議(非 SLA;與工程體積、外掛數量強相關)。需要多地域或並聯席位擴容時,參考 TCO 文中的節點與並聯策略,本篇不展開六地橫評。
| 檔位 | 建議並行 | 適合綁定的 label | 風險點 |
|---|---|---|---|
| M4 16GB | 1× macos-node 或 1× 輕量 Swift;避免雙 job 同時跑。 |
openclaw-macos-node + openclaw-m4-16 |
記憶體壓力導致 Vitest OOM;DerivedData 與 pnpm store 搶磁碟。 |
| M4 24GB | 1× macos-node + 1× 非峰值 Swift 檢查;或 2× node 分片錯開。 |
openclaw-m4-24;Swift 仍建議獨立 Runner 名。 |
並行 Swift 編譯仍可能觸發記憶體警告;應用 concurrency 分組。 |
| 雙機並聯 | 一台固定 node,一台固定 swift;用 label 路由,不用同一 Runner 混跑。 | openclaw-macos-swift 獨占 |
兩台機快取不共享;需各自預熱依賴。 |
Nuvcloud 提供多節點 M4 裸金屬、記憶體與 SSD 擴容選項,適合把上述標籤池做成固定 CI 席位;具體可用區與價格以 定價頁 與結帳頁為準,本文不承諾可用性或排隊 SLA。
六、Lobster 工作流:CI 失敗日誌 triage 可復現片段
Lobster 把多步工具鏈收成一次確定性呼叫,帶審批點與 resumeToken,適合「CI 紅了 → 拉日誌 → 分類 → 人工確認 → 發摘要」而非讓 LLM 逐步亂調工具。先在 Agent 設定裡 alsoAllow: ["lobster"],再下發 pipeline。
{
"action": "run",
"pipeline": "exec --json --shell 'gh run list --workflow ci.yml --limit 5 --json databaseId,conclusion,headBranch' | exec --stdin json --shell 'gh run view $ID --log-failed' | exec --stdin json --shell 'node scripts/ci-triage-summarize.mjs' | approve --preview-from-stdin --limit 3 --prompt '將摘要發到值班頻道?'",
"timeoutMs": 120000,
"maxStdoutBytes": 512000
}
對應 .lobster 工作流檔可把步驟拆為 collect → classify → approval → notify(見 Lobster 文件 workflow files 一節)。當 status 為 needs_approval 時,用 resume 繼續:
{
"action": "resume",
"token": "<resumeToken>",
"approve": true
}
可復現 triage 習慣:把每次失敗的 run_id、觸發的 label(如 openclaw-macos-node)、首段 stderr 雜湊寫入團隊 wiki;Lobster 輸出 JSON 進 issue 評論前,務必人工看一眼是否含 Secrets 片段。若 pipeline 逾時,按文件提高 timeoutMs 或拆分「拉日誌」與「LLM 總結」兩步。建議為每個失敗 run 保留 7 天唯讀歸檔,便於對比 flaky 與真實迴歸。
七、常見問題(FAQ)
Q1:Runner 顯示 Offline 怎麼辦?
檢查 launchd 服務是否執行、註冊 token 是否過期、磁碟是否滿。在 GitHub → Settings → Actions → Runners 移除後重新 config.sh;詳見 自建 Runner 文件。
Q2:macos-node 報 Node 版本不對?
對齊 Node 22:Runner 上 node -v、workflow setup-node、以及 checks-node-compat-node22 三者一致;清理舊的 ~/.npm 全域快取。
Q3:Swift / SDK 找不到?
確認完整 Xcode 已安裝且 sudo xcodebuild -license accept;macos-swift job 不要跑在僅 CLT 的機器上。
Q4:唯讀 Webhook 一直 403?
核對 secret、HTTPS 憑證、反代路徑;GitHub App 權限是否包含對應事件;閘道是否把 PR 正文誤當 shell 指令執行(應只解析中繼資料)。
Q5:與 openclaw doctor 怎麼區分?doctor 是安裝/閘道健康檢查;CI 紅在 Actions job 日誌。用 Lobster + gh run view 排 CI,不要用 onboard 文件替代 workflow 排障。
Q6:能否只跑 Linux、跳過 macOS?
可以合併純 Node 改動,但合併 Swift/ macOS 相關 PR 前必須至少手動 workflow_dispatch 一次全量,否則與上游 preflight 意圖衝突。
Q7:fork 與上游共用 Runner 安全嗎?
不建議。上游 PR 與 fork 應分 Runner 組、分 Secrets;防供應鏈腳本讀取 fork 外的簽章材料。
Q8:Lobster 回傳 invalid JSON?
確保 pipeline 每步 stdout 僅為 JSON;增大 maxStdoutBytes;檢查是否把人類可讀日誌直接 pipe 進下一步而未用 --json 包裝。
Q9:託管與自建能否混用?
可以:例如 PR 用託管、main 的 macos-swift 用自建;用 if: 或不同 workflow 檔區分。
更多文章見 技術部落格 索引。
在雲端 Mac mini 上,OpenClaw CI 更穩、更易擴容
把 macos-node / macos-swift 放到遠端獨享 M4 上,本質是買下可預測算力與標籤池彈性:Nuvcloud 裸金屬 Mac mini 提供原生 Unix、適合 7×24 Runner 的低功耗穩定性,並可按需升級 24GB、擴容 SSD 或並聯第二台專跑 Swift lane——與唯讀 Webhook + Lobster triage 組合時,DevOps 不必再盯託管佇列。
若你正在為 OpenClaw fork 規劃 CI 池,從一台帶 openclaw-macos-node 標籤的 M4 開始最省事——查看套餐與節點,再按本篇清單註冊 Runner 與 Webhook。