症狀:相同程式碼反覆編譯很慢,先不要急著增加遠端 Mac;等待空閒節點、UI 測試或簽名才是主要耗時,快取也救不了佇列。
最快解法:先用 Xcode Build Timing Summary、快取命中狀態與 CI 佇列紀錄拆開瓶頸;重複編譯占主導就試用 Tuist Xcode Cache,節點等待占主導就擴充或拆分遠端 Mac,兩者並存則採用雙軌。
這篇適合大型 iOS/macOS 專案的開發者、需要維護自託管 Mac CI 的 DevOps 工程師,以及要為研發團隊決定採購、租用或優化節點的平臺負責人。你不需要先接受某個方案,而是要把「編譯慢」與「流水線交付慢」分開取證。
注意: 截至 2026 年 9 月 15 日,Tuist 官方文件已確認 Xcode Cache 可共享 Xcode 編譯產物,但沒有提供適用所有專案的通用命中率或提速比例。近期傳輸機制的變更也不能直接推導成每個專案都會有相同收益。Tuist Xcode Cache 官方指南 與 2026 年 9 月 8 日的變更記錄 是本文判斷的主要依據。
SECTION 01先把「構建慢」拆成五種時間
同一個 CI 任務的總耗時,至少要分成以下幾段記錄,否則你可能把快取有效,卻仍然交付緩慢的情況誤判成設定失敗:
- 編譯時間:Swift、Objective-C、模組或依賴實際產生編譯產物的時間。
- 快取傳輸時間:向遠端服務上傳、下載、解壓或重組產物的時間。
- Runner 佇列時間:工作已送出,但仍在等待可用或符合條件的 Mac 節點。
- 測試執行時間:Simulator、UI 測試、裝置測試及測試後腳本所需的時間。
- 有效交付時間:從提交進入流水線,到你真正取得測試結果、封裝檔或可發布產物的時間。
先在 Xcode 的 Build Timing Summary 觀察冷構建與增量構建,再把依賴解析、腳本階段及測試階段獨立標記。Apple 的增量構建優化文件說明了如何查看及改善增量建置;它不等於 Tuist Cache 的命中保證。
如果主要時間集中在可重複的編譯工作,快取值得做對照試驗。如果時間集中在依賴解析、產生程式碼或自訂腳本,應先修正專案流程;只開啟 Tuist Xcode Cache,通常不會自動消除這些階段。
SECTION 02Tuist Xcode Cache 的適用範圍
Tuist Xcode Cache 的有效範圍,首先是能以相同輸入重用的 Xcode 編譯產物,例如反覆編譯未改動的依賴或模組。它適合處理「同一個提交在乾淨環境重建,卻一再產生相同編譯工作」的情況。
但以下工作不能直接視為可快取的編譯收益:
- 需要實際啟動 Simulator 或裝置的測試;
- UI 測試中依賴圖形工作階段、執行時版本或測試資料的部分;
- Archive、Export 及程式碼簽名;
- 依賴私密憑證、Keychain、臨時檔案或特定路徑的腳本;
- 每次都會改變輸入的版本資訊、產物路徑或環境變數。
Apple 對 Simulator 與實體裝置測試的說明,可協助你確認哪些步驟必須在實際執行環境中完成,而不是把所有工作都當作編譯。Apple Simulator 與裝置測試說明指出,測試所依賴的執行環境本身就是獨立的限制。
因此,對「Xcode 構建慢應先開快取還是增加 Runner」的判斷是:先看編譯區段占比。若重複編譯是主因,先建立小範圍快取試驗;若 Runner 尚未分配就已等待很久,先處理容量與路由;若兩段都長,兩者同時治理,但仍要分別記錄收益。
SECTION 03快取命中率不高,應該立即停用嗎?
不應只看一個命中百分比決定去留。你要先確認「未命中」究竟是本地沒有、遠端沒有,還是因為輸入根本不一致。
在同一提交、同一工具鏈及同一任務範圍內,逐項核對:
- Xcode 的快取設定是否已在實際 CI 工作中生效;
- CI 是否能以正確身份連線遠端快取服務;
- 上傳策略是否真的允許產物進入共享快取;
- 任務狀態是否區分本地命中、遠端命中與未命中;
- 編譯參數、目標架構、SDK、工具鏈版本及檔案路徑是否一致;
- 產物是否因環境變數、分支名稱或臨時路徑變成不同輸入。
Tuist 的 CI 說明涉及身份驗證與自動化接入,應以實際 CI 平臺的憑證與權限紀錄交叉核對,而不是只看工作日誌最後一行。Tuist CI 認證說明可作為核查入口。
如果命中不高,但每次命中的任務確實減少了編譯時間,而且上傳與下載沒有反過來吃掉收益,可以保留快取並先修正輸入穩定性。相反地,若每次命中都只是偶發、產物輸入持續漂移,停止條件應是先修專案可重現性,而不是無限增加快取容量。
SECTION 04傳輸成本是否已抵消編譯收益?
快取並非免費的零秒路徑。當節點與快取端點之間的網路距離較遠,或產物體積很大時,CPU 編譯時間可能只是被下載、解壓及驗證時間取代。
你可以在一次乾淨 CI 任務中分別記錄:
- 開始尋找快取的時間;
- 遠端命中回應時間;
- 下載或上傳開始與結束時間;
- 產物解壓、重組及後續編譯時間;
- 整個工作從 Runner 開始執行到交付的時間。
Tuist 在變更記錄中描述了分塊重用等傳輸機制。它減少的是重複傳輸工作,不代表所有專案都會得到相同比例的構建提速。Tuist 分塊重用變更記錄應被用來理解機制,而不是用來替代你的專案實測。
你可以按以下條件處置:
- 編譯明顯下降,傳輸只占小部分:保留遠端快取。
- 編譯下降,但下載成為主要新瓶頸:限制上傳範圍,或把快取端點移到更合適的地域。
- 快取未命中且仍要支付上傳成本:暫時關閉無效的上傳策略,先修正輸入一致性。
- 本地節點與快取端點路由不穩定:先處理頻寬、DNS、代理及權限,再談快取命中。
這也是為什麼「有命中」不等於「流水線一定更快」。你要比較的是有效交付時間,而不是只截取快取服務顯示的成功狀態。
SECTION 05遠端 Mac CI 的佇列與編譯慢,怎樣分辨?
佇列問題通常發生在 Runner 尚未真正開始執行工作之前;編譯問題則發生在節點已接手任務之後。把兩者混在一起,會導致你反覆調整編譯旗標,卻沒有增加任何可用容量。
在 CI 平臺保留以下紀錄:
- 工作進入佇列的時間;
- Runner 被選中及開始執行的時間;
- 實際 Xcode 編譯開始與結束時間;
- 測試、封裝及簽名的開始與結束時間;
- Runner 離線、標籤不匹配或權限拒絕的事件。
自託管 Runner 的標籤、線上狀態與工作路由會直接影響任務能否被分配。GitHub Actions 自託管 Runner 規則是檢查路由條件的權威依據。
一個常見場景是:Tuist Cache 已經在重複編譯上產生命中,但發布任務仍長時間等候具備簽名環境的 Mac。這不是快取失效,而是「可重用產物」與「可接收敏感任務的節點」屬於不同資源。
此時你應把佇列拆成至少三類:
- PR 構建:追求短回饋,優先安排可快取的編譯節點;
- 定時任務:可接受較長等待,避免搶占互動式回饋容量;
- 發布任務:隔離憑證、Archive 及簽名環境,不能只靠快取解決。
當等待空閒 Mac 是主要時間,增加或租用遠端 Mac 節點比繼續調整快取更直接。若你正在評估節點的啟動、重啟及交付條件,可先參考 MACNOX 的遠端 Mac 方案,但仍應用你的實際工作負載驗收。
SECTION 06UI 測試與簽名任務能靠 Tuist Cache 加速嗎?
Tuist Cache 可以縮短其中可重用的編譯部分,但不能讓 UI 測試、Simulator 啟動、Archive 或簽名步驟消失。Apple 的歸檔排查文件也把憑證、佈建設定及封裝環節列為獨立問題來源。Apple Archive 常見問題說明可用來核對發布池的失敗原因。
你可以用「構建池、測試池、發布池」三個邏輯邊界來判斷:
- 構建池:重點是工具鏈一致、快取輸入穩定及編譯回饋時間;
- 測試池:重點是 Simulator Runtime、圖形工作階段、測試資料及並行隔離;
- 發布池:重點是 Keychain、簽名憑證、Archive、Export 及權限控管。
若長任務會獨占圖形工作階段,增加快取不會讓同一個節點同時處理另一個 UI 測試。若簽名任務因憑證保護不能共用環境,就應隔離發布池,而不是把敏感資料放進可廣泛重用的快取流程。
SECTION 07用一次對照試跑決定快取、擴容或雙軌
不要用不同提交、不同 Xcode 版本或不同測試範圍比較前後結果。對照試跑至少要固定:
- 同一個提交;
- 同一套 Xcode、SDK、Tuist 與 Swift 工具鏈;
- 同一個目標架構;
- 同一組構建、測試及簽名步驟;
- 同一類型的遠端 Mac Runner。
然後各自記錄冷構建、快取命中、快取未命中、傳輸、佇列、測試與有效交付時間。以下清單可直接放進 CI 驗收單:
- [ ] 用 Build Timing Summary 找出最長的編譯目標,而不是只看整體工作時間。
- [ ] 對同一提交執行無快取與有快取的對照任務。
- [ ] 在工作日誌中確認本地命中、遠端命中及未命中狀態。
- [ ] 分開記錄快取上傳、下載與解壓時間。
- [ ] 記錄 Runner 進入佇列、開始執行及離線的時間點。
- [ ] 把 Simulator、UI 測試、Archive 與簽名從編譯時間中拆出。
- [ ] 為每個方案寫下停止條件與回退入口,避免無限調參。
決策可以收斂成三種:
- 先保留並優化快取:重複編譯下降,命中輸入穩定,佇列可控,且傳輸沒有成為主瓶頸。
- 先增加或拆分遠端 Mac:Runner 佇列、UI 測試或簽名占主導,快取只能縮短其中一小段。
- 採用快取與擴容雙軌:編譯確實受益,但交付仍被節點容量限制;保留快取,同時將構建、測試與發布池分流。
停止條件也要明確:若連續對照中快取輸入持續變動,就回退到修正專案設定;若佇列在快取優化後仍是主要耗時,就停止繼續調整快取並處理節點容量;若測試或簽名失敗與編譯產物無關,就回到對應執行池排查。
若你的現有方案是本地 Mac 加上 Linux 雲端伺服器,常見缺點是 macOS 專屬工具鏈不能集中管理、Linux 節點無法取代 Xcode 與 Simulator,而本地 Mac 也可能因關機、網路或單機佔用令 CI 中斷。這類情況下,租用 MACNOX 的遠端 Mac 可提供更容易持續在線的真實 macOS 節點;但若你需要長期滿載、固定實體介面或完全掌控硬體,購買 Mac 仍可能更合適。若只是要做短期擴容、驗證快取策略或承接發布高峰,可先從 MACNOX 的遠端 Mac 價格方案核對租用週期,再按上述清單驗收,而不是先假定增加節點必然有效。