動態執行

動態執行是 Bazel 自 0.21 版起的一項功能。在這個版本中,相同動作的本機和遠端執行作業會平行執行,並使用完成的第一個分支版本的輸出內容,取消另一個分支版本。它結合了遠端建構系統的執行能力和/或大型共用快取與本機執行作業的延遲時間較短,因此可為清除與漸進式建構作業提供最佳解決方案。

本頁面說明如何啟用、調整動態執行功能及進行偵錯。如果您同時設定了本機和遠端執行作業,且想要調整 Bazel 設定以提升效能,請參閱本頁內容。如果您尚未設定遠端執行,請先參閱 Bazel 的遠端執行總覽

要啟用動態執行功能嗎?

動態執行模組是 Bazel 的一部分,但為了利用動態執行,您必須已經能夠透過相同的 Bazel 設定在本機和遠端編譯。

如要啟用動態執行模組,請將 --internal_spawn_scheduler 標記傳遞至 Bazel。這會新增名為 dynamic 的新執行策略。您現在可以使用此方法做為要動態執行的記憶指令 (例如 --strategy=Javac=dynamic) 策略。請參閱下一節,瞭解如何選擇要啟用動態執行的記憶功能。

針對使用動態策略的任何記憶,遠端執行策略取自 --dynamic_remote_strategy 旗標和來自 --dynamic_local_strategy 標記的本機策略。傳送 --dynamic_local_strategy=worker,sandboxed 會設定動態執行作業本機分支版本的預設值,以便按照該順序試用工作站或沙箱執行作業。傳遞 --dynamic_local_strategy=Javac=worker 會覆寫 Javac 助聽器的預設值。遠端版本的運作方式相同。您可以多次指定這兩個標記。如果動作無法在本機執行,則會照常從遠端執行,反之亦然。

如果遠端系統有快取,--local_execution_delay 旗標會在遠端系統指出快取命中後,將延遲時間 (以毫秒為單位) 新增至本機執行作業。避免在可能產生更多快取命中時執行本機執行作業。預設值為 1000 毫秒,但應該改為維持比快取命中時間稍長一些。實際時間取決於遠端系統和往返時間。通常,指定遠端系統的所有使用者值都相同,除非其中有些使用者已足夠增加往返延遲時間。您可以使用 Bazel 剖析功能,查看一般快取命中的所需時間。

動態執行功能可與本機沙箱策略搭配使用,也可與永久工作站搭配使用。永久工作站與動態執行搭配使用時,會自動以沙箱機制執行,且無法使用 multiplex 工作站。在 Darwin 和 Windows 系統中,沙箱策略速度可能較為緩慢;您可以傳遞 --reuse_sandbox_directories 來減少在這些系統上建立沙箱的負擔。

動態執行也可以透過 standalone 策略執行,但由於 standalone 策略必須在執行時採用輸出鎖定,因此可以有效阻止遠端策略結束執行。--experimental_local_lockfree_output 旗標的作用是解決這個問題,可讓本機執行作業直接寫入輸出內容,但這樣在先完成遠端執行作業時,便能取消這個作業。

如果動態執行作業的其中一個分支先完成,但發生錯誤,整個動作就會失敗。這是刻意的選擇,防止本機和遠端執行之間的差異。

如要進一步瞭解動態執行和鎖定的運作方式,請參閱 Julio Merino 的優質網誌文章

何時該使用動態執行?

動態執行需要某種形式的遠端執行系統。目前無法使用快取專用遠端系統,因為系統會將快取失敗視為失敗的動作。

並非所有動作類型都適合遠端執行。最理想的候選項目是在本機上運作速度更快的項目,例如透過永久工作站運作,或是執行速度足以讓遠端執行負擔大幅縮短執行時間的計畫。由於每個本機執行的動作都會鎖定一些 CPU 和記憶體資源,因此執行不符合這些類別的動作只會延遲執行。

自版本 5.0.0-pre.20210708.4 推出,效能剖析包含工作站執行作業的相關資料,包括在失去動態執行競賽後完成工作要求所花費的時間。如果您發現動態執行工作站執行緒花費大量時間取得資源,或是在 async-worker-finish 中長時間使用,表示本機動作可能會延遲工作站執行緒執行得很慢。

剖析動態執行效能不佳的資料

在上述使用 8 個 Javac 工作站的設定檔中,我們發現許多 Javac 工作站在 async-worker-finish 執行緒上失去競賽,並且完成工作。這是因為非工作站記憶力花費足夠資源延遲工作站。

以更優異的動態執行效能來剖析資料

如果只有 Javac 是以動態執行執行,則只有約一半的工作站在開始工作後最終會失去競賽。

先前建議的 --experimental_spawn_scheduler 旗標已淘汰。它會開啟動態執行功能,並將 dynamic 設為所有記憶方法的預設策略,這樣通常會導致這類問題。

疑難排解

動態執行的問題可能難以偵錯,也難以偵錯,因為這類問題只能觸發本機和遠端執行作業的特定組合。--debug_spawn_scheduler 會從動態執行系統新增額外輸出內容,協助對這些問題進行偵錯。您也可以調整 --local_execution_delay 旗標,以及遠端和本機工作的數量,以便更輕鬆地重現問題。

如果您在使用 standalone 策略進行動態執行時遇到問題,請嘗試在不使用 --experimental_local_lockfree_output 的情況下執行,或在沙箱環境中執行本機動作。這可能會減慢建構速度 (如果您使用 Mac 或 Windows,請參閱上述說明),但會移除部分可能失敗的原因。