要撰寫的測試項目

測試有助於找出程式碼中的潛在問題,各種類型的測試則提供不同程度的涵蓋範圍。

本文件為開發人員 (元件作者、驅動程式庫程式作者和 API/ABI 維護人員) 提供驗證 Fuchsia 軟體的基本測試。

下表概略說明這些測試類型的測試類型。

原始碼 元件 驅動程式 通訊協定
單位 全部 - - -
整合 - 全部 部分 -
相容性 (CTF) - 部分 部分 所有 (SDK)
規格符合性 - 部分 全部 部分
平台預期情況 - 部分 部分 部分
系統互動 (產品) - 部分 部分 部分

以下各節會依據下列條件將測試類型分類:

  • 需求條件 (哪些原始碼、套件或元件需要這類測試)
  • 測試內容
  • 主要優點
  • 如何查看涵蓋率 (如何判斷這項測試是否有效,並評估其影響)
  • 實作方式 (開發人員需要採取哪些動作才能獲得這項涵蓋率)
  • 負責撰寫這類測試的人員 (負責提供這類測試的人員)
  • 來源儲存位置 (測試放置的位置)
  • Fuchsia 何時執行這類測試 (在發布管道中是這類測試)

單元測試

  • 必要條件:所有原始碼
  • 測試內容:個別軟體單元的程式碼合約
  • 主要優點:允許更有效率的重構、最佳化和開發。
  • 如何查看涵蓋範圍:https://analysis.chromium.org/coverage/p/fuchsia
  • 導入方式:使用您選擇的語言測試架構
  • 由誰編寫這類測試:所有元件/驅動程式庫擁有者
  • 來源儲存位置:緊鄰要測試的程式碼
  • Fchsia 何時會執行這類測試:Commit-Queue 和 持續整合。

所有程式碼都應該採用能夠驗證功能的最低可能測試。我們使用的語言中的許多函式和類別,可以藉由聚焦於小型的單元測試直接測試合約。

單元測試是熟悉的領域,因此大部分的 Fuchsia 開發人員均可針對自己選擇的語言使用任何測試架構,但有幾項明顯差異:

  • 在裝置 (裝置測試) 上執行的測試會以 Fauchsia 套件發布,並在測試管理員管理的環境中執行。根據預設,這些測試完全密封,與系統的其他部分隔離,任何其他測試都無法看到測試輸出的檔案。
  • 裝置測試可能會公開由 ffx test 串流至主機裝置的自訂成果
  • 針對產生涵蓋率資訊的裝置測試編譯後,系統會自動將資料串流從裝置外部。ffx coverage 等工具可協助自動化資料處理作業。涵蓋範圍資訊會顯示在 Gerrit 和 Fuchsia Coverage 資訊主頁,以用於樹狀結構內測試,而 OOT 測試執行工具則需要自己的指令碼來處理測試的涵蓋率輸出內容。

請參閱驅動程式單元測試快速入門指南,瞭解如何編寫驅動程式單元測試。

下圖顯示在 Fuchsia 系統中執行的單元測試。 單元測試

整合測試

整合測試會檢查某個元件的介面和行為,是否能與呼叫該元件的其他元件一起運作。驗證不同的元件是否能像系統一樣搭配運作,並正常互動。

系統會針對要測試的元件驗證下列情境:

  • 不過,前者可以啟動及回應要求
  • 回應會如預期回應
  • 會照常與其依附元件互動
  • 如果驅動程式庫是由多個元件組成,請檢查驅動程式庫內部元件是否正常運作

建議使用 Test Realm Factory 以完全 (單獨) 方式執行整合測試,但也可以視需要在不對等的情況下執行。

密封整合測試

  • 必備條件:所有元件和許多驅動程式
  • 測試內容:執行階段行為和合約
  • 主要優點:確保元件或驅動程式庫可以啟動、自行初始化,並與依附元件互動
  • 如何查看涵蓋範圍:https://analysis.chromium.org/coverage/p/fuchsia。 請注意,OOT 用途需要變更建構選項,才能輸出涵蓋範圍資訊並加以處理。
  • 實作方式: 測試 Realm 工廠
  • 寫入這類測試的人員:所有元件作者、許多驅動程式庫開發人員
  • 來源儲存位置:緊鄰要測試的程式碼
  • Fchsia 何時會執行這類測試:Commit-Queue 和 持續整合。

單元測試是小型且專注於商業邏輯的特定部分,但整合測試主要是集中測試軟體模組之間的互動情形。

整合測試是另一個眾所皆知的區域,但 Fuchsia 提供的測試功能與其他作業系統截然不同。尤其是以 Zircon 的功能型安全性原則為基礎,F Fuchsia 的元件架構強制明確使用及轉送「功能」。最終結果是 Fuchsia 測試可以明顯密封且以遞迴對稱,這些屬性的影響稱為「小菲的測試超能力」。測試之間可以完全獨立,且元件能以任意巢狀結構組成。也就是說,一或多個 Fuchsia 子系統可能會在獨立的測試環境中執行 (例如 DriverTestRealmTest UI Stack)。

下圖顯示使用測試 Realm 模式的密封整合測試。 整合測試

根據預設,所有 Fuchsia 上的測試皆為密封測試,這表示它們會自動受益於可證實的遺傳性,以及任意建立巢狀依附元件的功能。

密封整合測試只需以這個基礎為基礎,即可在獨立的測試環境中執行元件或驅動程式庫程式,並使用 FIDL 通訊協定與其互動。這些測試涵蓋元件/驅動程式庫的下列情境:

  1. 不過,前者可以啟動及回應要求
  2. 回應會如預期回應
  3. 會照常與其依附元件互動

如要編寫密封整合測試,建議採用 Test Realm Factory (TRF) 模式,此模型可為測試準備在不同類型測試中重複使用。TRF 測試包含三個部分:

  1. 測試運作範圍,是測試中元件的獨立執行個體,以及所有依附元件。
  2. 測試套件,與測試領域互動,並對其狀態做出斷言。
  3. 每個測試套件專屬的 RealmFactory 通訊協定,用來建構測試領域。

測試套件中的每個測試案例都會在 RealmFactory 上呼叫方法,以建立測試領域、與該領域互動,並針對其公開的功能進行互動,並在收到的回應中斷言。TRF 文件提供使用 testgen 工具的操作說明,自動建立上述結構的骨架並填入詳細資料。

使用 TRF 的密封整合測試奠定了以下許多類型的測試的基礎。

所有元件和許多驅動程式都需要整合測試,這些測試皆應使用 TRF。

非密封整合測試

  • 需要功能:部分元件和驅動程式。特別是具有難以模擬或隔離的依附元件 (例如 Vulkan)。
  • 測試內容:系統行為和合約
  • 其主要優點:確保元件或驅動程式庫可以啟動、自行初始化,並與依附元件互動,即使其中某些依附元件是整個系統性和非密封的依附元件也是如此。
  • 如何查看涵蓋範圍:https://analysis.chromium.org/coverage/p/fuchsia。 請注意,OOT 用途需要變更建構選項,才能輸出涵蓋範圍資訊並加以處理。
  • 實作方式: 測試 Realm 工廠
  • 寫入這類測試的人員:部分元件和驅動程式庫作者
  • 來源儲存位置:緊鄰要測試的程式碼
  • Fchsia 何時會執行這類測試:Commit-Queue 和 持續整合。

雖然我們應該努力達成密封整合測試,但某些測試很難有質感。這通常是因為這類測試對於尚未以隱密封裝方式編寫的依附元件較為困難。舉例來說,我們尚未提供 Vulkan 的高保真度模擬,因此允許特定測試存取整個系統的 Vulkan 功能。

下圖顯示了與外部系統、元件或驅動程式庫互動的非密封整合測試。 整合測試

存取系統功能的測試稱為非密封整合測試。雖然在技術上並不密封,但仍應盡可能加以隔離:

  1. 僅仰賴執行測試所需的能力。
  2. 遵循 Test Realm Factory 樣式,一般需要使用系統中的依附元件功能,而非隔離。
  3. 偏好依賴能盡力為用戶端區隔的功能 (例如不同的結構定義或工作階段) 的功能。
  4. 測試完成後,請清除狀態。

非密封整合測試必須在元件拓撲的位置執行,元件拓撲必須已轉送所需的功能。如需現有位置的清單和新增位置的操作說明,請參閱這裡

使用非密封的整合測試時,請謹慎使用,且適用於沒有密封解決方案的情況。最好將這類測試用做定時差解決方案,在測試時運用適當的模擬或隔離功能進行密封。這些解決方案應用於合法要求全球宣告特定系統行為的測試 (請改為參閱裝置端系統驗證主機驅動系統互動測試)。

相容性測試 (CTF)

  • 什麼需求:在 SDK 中公開的通訊協定,但也適用於用戶端程式庫和工具。
  • 測試內容:平台 ABI/API 行為一致性和相容性
  • 用途的主要優點:確保平台通訊協定的行為不會產生不相容的意外變更。特別重視平台穩定性。
  • 如何查看涵蓋率:CTF 涵蓋率資訊主頁。
  • 實作方式:編寫測試 Realm Factory (TRF) 整合測試,並啟用 CTF 模式
  • 負責編寫這類測試的人員:SDK 通訊協定實作的所有擁有者
  • 來源儲存位置:fuchsia.git
  • Fchsia 何時會執行這類測試:Commit-Queue 和 持續整合。

相容性測試提供早期警示,說明平台變更可能會導致下游服務中斷,並確保平台 ABI 保持穩定至關重要。一般來說,由 SDK 公開的每個 FIDL 通訊協定穩定 API,應針對其 API 級別執行相容性測試。

這些測試會驗證通訊協定的用戶端、指定穩定的 API 級別並以 SDK 建構,確保接收與預期相容的平台。

FIDL 通訊協定會隨著時間的推移而在其指定的介面及其行為方面發展。如果某些通訊協定的輸出內容與先前的預期不同,就會發生這項常見的錯誤。

僅使用整合測試找出這些錯誤並不容易,因為測試時通常會在測試時一併更新。此外,在 SDK 中公開的 API 修訂版本之間,也必須維持一定程度的相容性。

Fuchsia (CTF) 的相容性測試可讓元件實作的不同版本,根據不同的相容性測試期望測試相容性。TRF 模式已與 CTF 完全整合,且可透過設定變更指定 TRF 測試來進行相容性測試,無須變更來源。

機制如下:

  • 針對 Fuchsia 的每個里程碑版本 (F#),保留在該里程碑下的測試套件。
  • 針對每個平台變更,針對每個里程碑版本,對 RealmFactory 執行每個保留的測試套件。

最終的結果是,公開通訊協定行為的舊預期會隨日後的修改而維持。未能提供這類涵蓋範圍,表示如果 SDK 通訊協定的行為或介面有些微幅變更,會導致下游中斷 (尤其是造成根本原因難以處理) 的下游中斷情形。

下圖顯示使用 Test Realm Factory (TRF) 模式和凍結元件假造的相容性測試。 相容性測試

為 TRF 測試啟用 CTF 模式是簡單的設定選項,您可以將現有的整合測試轉換為 TRF (範例)。實作 SDK 通訊協定的元件/驅動程式作者應優先將其測試轉換為 TRF,並啟用 CTF 模式來穩定 Fuchsia 平台,並省下持續進行的大規模變更負擔。

在合作夥伴或公用 SDK 中公開通訊協定的所有元件都應執行 CTF 測試。

規格符合測試

  • 需求:樹狀外 (OOT) 驅動程式、從一個實作遷移至另一個實作的元件,以及 (一些) 架構用戶端。
  • 測試內容:不同通訊協定或程式庫實作項目之間的一致性,以確保符合規格。
  • 主要優點:確保同一個介面的不同實作方式可展現相容行為。如果同一介面有多個實作者,這項功能就特別實用。
  • 查看涵蓋範圍:TODO
  • 實作方式:使用現有 TRF 整合測試的一部分來建立新的 TRF 測試。或者,您也可以在 Lacewing 中編寫測試,與完整的系統互動。
  • 由誰編寫這類測試:合約/通訊協定的擁有者會定義需求條件的測試,然後下游使用者會重複使用或組合該測試,確保程式碼符合需求。
  • 來源儲存位置:fuchsia.git 或透過 SDK 在獨立存放區中建構
  • Fchsia 何時執行這類測試:Commit-Queue、樹狀結構外持續整合。

Fuchsia Platform 定義了一個須由一或多項實作項目實現的合約,其中有些可能是由 fuchsia.git 存放區以外的定義:

  1. Fuchsia SDK 會定義必須由 Fuchsia 來源樹狀結構 (不在樹狀結構外) 內的驅動程式實作的驅動程式庫 API。駕駛人員產生的結果必須符合平台的預期。
  2. 元件重寫程序包含一個現有和進行中的程式碼集,而且其程式碼集必須保持一致。例如,在重新編寫檔案系統儲存空間堆疊時,我們希望確保寫入及讀取檔案產生的結果與原始實作一致。
  3. 檢查和記錄等用戶端程式庫是以多種語言實作,實作項目包括編寫二進位格式。無論產生程式庫的程式庫為何,LOG("Hello, world") 動作都必須產生與二進位檔相容的輸出內容。

請務必瞭解實作內容是否符合規格要求,並利用規格一致性測試來驗證這種情況。

符合規格一致性測試的密封方法

我們會針對驅動程式庫進行演練並檢查預期行為,以測試驅動程式庫程式是否符合預期。如果駕駛人控制裝置,就必須在硬體上執行 (建議做法)。這是由駕駛人在桌上 (硬體上) 和 CI/CQ 使用 SDK 執行

規格一致性測試可以在 TRF 測試的基礎上進行,與相容性測試相同的結構。在這種情況下,主要的差異在於 TRF 測試的不同部分的使用方式。

規格合規性測試的建議模式為定義 RealmFactory (包含測試下的實作)、測試套件 (驗證規格實作),且無論合約定義為何 (例如適用於 SDK 通訊協定的 fuchsia.git),以及用於執行測試的 FIDL 通訊協定 (負責將測試中的一組元件執行個體化並進行互動)。測試套件和 FIDL 通訊協定會發布至實作者 (例如透過 SDK)。實作合約的開發人員可以使用分散式測試套件,並實作自己的 RealmFactory,來將實作包裝在 FIDL 通訊協定後方。換句話說,每個實作項目都會套用定義合約的確切測試組合。

下圖顯示以密封方式執行規格一致性測試的方法。 規格合規測試 (密封)

符合規格合規性測試的非密封方法

測試規格一致性的非密封方法,是在使用 Lacewing for (硬體相依實作) 的工作系統上執行測試。這由開發人員在 CI/CQ 中按照產品導入作業執行。

下圖說明以非密封方式執行規格一致性測試的方法。 規格合規測試 (非密封)

主機驅動規格一致性測試的方法

或者,規格一致性測試可以使用 Lacewing 進行編寫,並以主機導向的系統互動測試的形式執行。如果通訊協定的實作器是驅動程式庫,或以特定硬體為依據,這種做法特別實用。這特別適合用來斷言產品圖片 (包括驅動程式庫符合規格,且經過妥善組合,以便支援與硬體互動。

下圖以主機驅動的方式執行規格一致性測試的方法。 規格合規測試 (主機驅動)

更具體地說,我們可以按照下列方式解決上述範例:

  1. 驅動程式:在 fuchsia.git 中定義驅動程式庫 FIDL。使用相關聯的 Test Suite 和 FIDL 通訊協定建立 TRF 測試,並傳送至 SDK 中。在樹狀結構外驅動程式庫存放區中實作驅動程式庫,建立涵蓋驅動程式庫的 RealmFactory,並實作測試 FIDL。針對該 RealmFactory 執行分散式測試套件。
  2. 驅動程式 (Lacewing):建立與來自主機的驅動程式 FIDL 通訊協定互動的 Lacewing 測試。將此測試以二進位構件的形式提供,可在樹狀結構外驅動程式庫存放區中或產品組合期間執行。
  3. 元件重新編寫:建立新的程式碼集來重新編寫,並使用現有實作的 Test Suite,建立實作測試 FIDL 的基本架構 TRF 測試 (遵循最佳做法以傳回非失敗的 UNSUPPORTED 值)。逐步重新編寫元件,隨著測試案例開始讓這些情況開始通過封鎖,以封鎖這些情況。所有測試案例都通過後,重新寫入作業就會完成,並刪除舊的實作。
  4. 多種語言的用戶端程式庫:將程式庫中可能執行的作業定義為測試 FIDL。為其中一個程式庫實作建立 TRF 測試,然後將該實作的 Test Suite 用於所有其他實作。所以它們仍符合規範。

預計多次實作的介面應提供規格符合測試,讓整合商以此為基礎進行建構。

平台預期測試

  • 需要功能:許多平台元件和驅動程式。舉例來說,駕駛人應確保在組合的系統中與實際硬體互動。
  • 測試內容:組合產品圖片上元件/驅動程式庫程式的行為
  • 主要優點:確保平台元件/驅動程式庫安裝在實際產品中時可正常運作。有助於找出能力轉送和與實際硬體互動的問題。
  • 查看涵蓋範圍:TODO
  • 實作方式:編寫測試領域工廠 (TRF) 整合測試、建立執行領域、啟用系統驗證模式 (TODO)。請對規格進行測試,並在管道的每個階段執行這些測試 (強烈建議重複使用)。運用平台期望測試套裝 (PETS)。
  • 負責編寫這類測試的人員:平台元件和驅動程式的擁有者
  • 來源儲存位置:fuchsia.git,會透過 SDK 運送至樹狀結構外存放區
  • Fchsia 何時執行這類測試:Commit-Queue、樹狀結構外持續整合。

下圖顯示測試搭配 SDK 使用的平台預期測試。

平台預期測試

密封整合測試可確保元件獨立執行可正確運作,但不會驗證組合的系統映像檔 (包括該元件) 是否正常運作。系統驗證測試是一種特殊的非密封整合測試,可確保實際元件在遵循一些限制的情況下運作。

平台預期測試一般是以包含 RealmFactory 和 Test Suite 的密封 TRF 測試為基礎。系統驗證測試會使用獨立元件提供實際系統功能的存取權,而非使用 RealmFactory (將測試中的獨立元件執行個體化) 。

舉例來說,如果您測試的是 fuchsia.example.Echo,密封的 TRF 測試就會提供可公開 fuchsia.example.test.EchoHarness 的 RealmFactory,讓您透過 CreateRealm() 取得獨立的 fuchsia.example.Echo 連線。系統驗證測試的獨立元件也會實作 CreateRealm(),但提供的「實際」 fuchsia.example.Echo 連線來自系統本身。

這個模式可讓您在密封和非密封的情況下使用完全相同的測試程式碼,但透過 UNSUPPORTED 傳回值處理不相容的問題。

如要瞭解這項作業的運作方式,除了 CreateRealm() 之外,我們還使用包含 SetUpDependency() 方法的管理工具進行系統驗證測試。如果在非密封設定中執行時無法設定依附元件,該方法只會傳回 UNSUPPORTED,並略過依附的測試。假設有 read_any_data()read_specific_data() 測試案例會略過呼叫 SetUpDependency() 並分別呼叫。後者可確保任何資料都能以正確格式 (密封或不雅) 讀取,而後者則能確保特定資料傳回 (純色)。

為協助 OOT 系統整合商,我們可能會在 SDK 中寄送系統驗證測試套件,以便針對組合過的產品映像檔 OOT 執行。這是驗證驅動程式編寫 OOT 的主要機制

平台元件和驅動程式應進行系統驗證測試。Fuchsia SDK 應提供驗證測試套件,供每個驅動程式庫在獨立存放區中實作。

系統互動 (產品) 測試

  • 必備條件:部分元件和驅動程式、個別使用者歷程 (例如在使用者輕觸螢幕時驗證回應)。
  • 測試功能:系統服務和個別使用者歷程中的行為迴歸。
  • 主要優點:可以完全掌控一部或多部 Fuchsia 裝置和非 Fuchsia 週邊裝置。涵蓋需要多部裝置、重新啟動裝置,或是模擬使用者與裝置互動的案例。
  • 查看涵蓋範圍:TODO
  • 實作方式:使用 Mobly/Lacewing 編寫 Python 測試
  • 由誰編寫這類測試:元件/驅動程式庫擁有者;產品擁有者
  • 來源儲存位置:fuchsia.git 或 OOT
  • Fchsia 何時執行這類測試:提交佇列、視需要使用 OOT 持續整合

Fuchsia 針對無法在其他系統上寫入的多種情況進行了密封測試,但在某些情況下,無法取代實際控制整個裝置的功能。比起在接受測試的裝置上執行這些測試,主機系統必須負責控制一或多部裝置,執行端對端程式碼路徑。

主機驅動的系統互動測試可以使用 SDK 工具完全控制 Fuchsia 裝置,並直接連線至裝置上的服務。是使用 Lacewing 架構 (在 Mobly 上建構) 編寫。

使用 Lacewing 的測試可以任意連線至目標系統上的服務。有些測試則是針對特定驅動程式或子系統 (例如即時時鐘可以在重新啟動後節省時間?) 而編寫的,目的是涵蓋需要針對裝置全面設定的使用者歷程 (例如,使用者只要登入網路瀏覽器並前往某個網頁),其中一些測試是用來控制 Fuchsia 和與非 Fachia 配件裝置搭配的 Fuchsia 和非 Fuchag 配件。

採用 Lacewing 架構時,系統會透過「預設用途」處理與裝置的互動,而此架構提供可調整的介面,能夠與特定裝置子系統互動 (例如藍牙功能提示、WLAN 服務資源等)。

圖表顯示使用 Lacewing 執行系統互動測試的方法。系統互動測試

與大多數的端對端 (E2E) 測試一樣,這類測試可能相當昂貴,原因如下:

  • 測試通常需要在特定真實硬體設定中執行。
  • E2E 測試的效能較差,這會增加 CI/CQ 延遲和負載。
  • E2E 測試未獨立運作,如果狀態未適當管理,就可能會增加不穩定的狀態。

基於上述原因,請謹慎進行 E2E 測試,但這通常是最後一道防線,涵蓋了最困難的測試缺口:確保實際使用者與系統互動時會看到所需的輸出內容。

部分系統元件和驅動程式需要這類測試,但使用 Lacewing 的主要優點是涵蓋獨立裝置端測試無法涵蓋的實際裝置互動。選擇系統驗證或「延遲」通常是判斷呼叫,但在完整的測試策略中,這兩種測試都有空間。測試作者應以最低的維護成本獲得所需的涵蓋率。