逐步解說:建立、編輯和維護自動程式碼 UI 測試
在這個逐步解說中,您將建立簡單的 Windows Presentation Foundation (WPF) 應用程式,以示範如何建立、編輯和維護自動程式碼 UI 測試。本逐步解說提供解決方案用來修正各種因時間問題和控制項重構而中斷的測試。
必要條件
在本逐步解說中,您將會需要:
- Visual Studio Ultimate 或 Visual Studio Premium。
建立簡單 WPF 應用程式
在 [檔案] 功能表上,指向 [新增],然後選取 [專案]。
[新增專案] 對話方塊隨即出現。
在 [已安裝的範本] 窗格中,展開 [Visual C#],然後選取 [Windows]。
在中間窗格上方,檢查目標 Framework 下拉式清單是否設定為 [.NET Framework 4.5]。
在中間窗格中選取 [WPF 應用程式] 範本。
在 [名稱] 文字方塊中輸入 SimpleWPFApp。
指定要儲存專案的資料夾。在 [位置] 文字方塊中輸入資料夾的名稱。
選擇 [確定]。
WPF Designer for Visual Studio 隨即開啟,並顯示專案的 MainWindow。
如果目前未開啟工具箱,請開啟它。選取 [檢視] 功能表,然後選取 [工具箱]。
在 [所有 WPF 控制項] 區段底下,將 [Button]、[CheckBox] 和 [ProgressBar] 控制項拖曳至設計介面中的 MainWindow。
選取 [Button] 控制項。在 [屬性] 視窗中,將 [Content] 屬性的值從 [Button] 變更為 [Start]。
選取 [ProgressBar] 控制項。在 [屬性] 視窗中,將 [Maximum] 屬性的值從 [100] 變更為 [1000]。
選取 [Checkbox] 控制項。在 [屬性] 視窗中,清除 [IsEnabled] 屬性。
選取按鈕控制項以加入 Click 事件。
MainWindow.xmal.cs 會顯示在 [程式碼編輯器] 中,而且游標位於新的 button1_Choose 事件。
在 MainWindow 類別的頂端,加入一個委派。這個委派將用於進度列。若要加入委派,請加入下列程式碼:
private delegate void ProgressBarDelegate( System.Windows.DependencyProperty dp, Object value);
在 button1_Choose 方法中,加入下列程式碼:
double progress = 0; ProgressBarDelegate updatePbDelegate = new ProgressBarDelegate(progressBar1.SetValue); do { progress ++; Dispatcher.Invoke(updatePbDelegate, System.Windows.Threading.DispatcherPriority.Background, new object[] { ProgressBar.ValueProperty, progress }); progressBar1.Value = progress; } while (progressBar1.Value != progressBar1.Maximum); checkBox1.IsEnabled = true;
確認 WPF 應用程式執行無誤。
在 [偵錯] 功能表上,選取 [開始偵錯] 或按 F5。
選取 [開始]。
進度列幾分鐘後應該 100% 完成。核取方塊控制項現已啟用。
關閉 SimpleWPFApp。
為 SimpleWPFApp 建立和執行自動程式碼 UI 測試
在 [方案總管] 中,以滑鼠右鍵按一下方案、選取 [加入],然後選取 [新增專案]。
[加入新的專案] 對話方塊隨即出現。
在 [已安裝的範本] 窗格中,展開 [Visual C#],然後選取 [測試]。
在中間窗格中選取 [測試專案] 範本。
選擇 [確定]。
在方案總管中,新的自動程式碼 UI 測試專案名為 [CodedUITestProject1] 加入至您的方案中。
[產生自動程式碼 UI 測試的程式碼] 對話方塊隨即出現。
選取 [錄製動作、編輯 UI 對應或加入判斷提示] 選項,然後選取 [確定]。
[UIMap –自動程式碼 UI 測試產生器] 隨即出現,因此, Visual Studio 視窗最小化。
如需對話方塊之選項的詳細資訊,請參閱 建立自動程式碼 UI 測試。
找出並執行先前建立的 SimpleWPFApp 應用程式。根據預設,這個應用程式將位於:C:\Users\<username>\Documents\Visual Studio 2012\Projects\SimpleWPFApp\SimpleWPFApp\bin\Debug\SimpleWPFApp.exe
建立 SimpleWPFApp 應用程式的桌面捷徑。以滑鼠右鍵按一下 SimpleWPFApp.exe,然後選取 [複製]。在桌面上按一下滑鼠右鍵,再選取 [貼上捷徑]。
提示 使用應用程式的捷徑可以輕鬆加入或修改應用程式的自動程式碼 UI 測試,因為它能讓您快速啟動應用程式。您不必巡覽就能找到它。在本逐步解說中,您將需要重新執行應用程式。
選取 [UIMap - 自動程式碼 UI 測試產生器] 上的 [開始錄製]。[自動程式碼 UI 測試產生器] 幾分鐘後會準備就緒。
使用桌面捷徑執行 SimpleWPFApp.exe。
SimpleWPFApp 中,選取 [開始]。
進度列幾分鐘後應該 100% 完成。核取方塊控制項現已啟用。
選取 [CheckBox] 控制項的方塊。
關閉 SimpleWPFApp 應用程式。
選取 [UIMap - 自動程式碼 UI 測試產生器] 上的 [產生程式碼]。
在 [方法名稱] 中輸入 SimpleAppTest,然後選取 [加入和產生]。自動程式碼 UI 測試幾分鐘後會出現並加入至方案。
關閉 [UIMap - 自動程式碼 UI 測試產生器]。
CodedUITest1.cs 檔案隨即出現在 [程式碼編輯器] 中。
執行自動程式碼 UI 測試
在 CodedUITest1.cs 檔案中找出 [CodedUITestMethod] 方法,然後按一下滑鼠右鍵再選取 [執行測試]。
當自動程式碼 UI 測試執行時,會顯示 SimpleWPFApp。它會處理您在先前程序執行的步驟。但是,當這個測試嘗試選取 [CheckBox] 控制項的核取方塊時,[測試結果] 視窗會顯示該測試失敗。這是因為這個測試嘗試選取核取方塊,但是一直到在進度列 100% 完成之後才發現 [CheckBox] 控制項已停用。您可以使用各種可供自動程式碼 UI 測試使用的 UITestControl.WaitForControlXXX() 方法,來修正這個 (或類似) 問題。下一個程序將示範使用 WaitForControlEnabled() 方法來修正導致這個測試失敗的問題。如需詳細資訊,請參閱讓自動程式碼 UI 測試在播放期間等候特定事件。
編輯和重新執行自動程式碼 UI 測試
在 [測試結果] 視窗中,以滑鼠右鍵按一下失敗的測試,然後選取 [檢視測試結果詳細資料]。
CodedUITestMethod1[Results] 隨即顯示。
在 [錯誤堆疊追蹤] 區段中,選取 [TestProject1.UIMap.SimpleAppTest()] 旁邊的第一個連結。
UIMap.Designer.cs 檔案隨即開啟,而且錯誤點反白顯示在程式碼中:
// Select 'CheckBox' check box uICheckBoxCheckBox.Checked = this.SimpleAppTestParams.UICheckBoxCheckBoxChecked;
若要修正這個問題,您可以使用 WaitForControlEnabled() 方法,讓自動程式碼 UI 測試先等候 [CheckBox] 控制項完成啟用後再繼續進行至這一行。
警告 請勿修改 UIMap.Designer.cs 檔案。每次您使用 [UIMap - 自動程式碼 UI 測試產生器] 產生程式碼時,對 UIMapDesigner.cs 檔案中的程式碼所做的變更都會被覆寫。如果您需要修改錄製的方法,必須將它複製到 UIMap.cs 檔案並重新命名。UIMap.cs 檔案可用來覆寫 UIMapDesigner.cs 檔案中的方法和屬性。您必須移除 Coded UITest.cs 檔案中原始方法的參考,並將它取代為重新命名的方法名稱。
在 [方案總管] 中,找出自動程式碼 UI 測試專案中的 UIMap.uitest。
開啟 [UIMap.uitest] 的捷徑功能表並選取 [開啟]。
此自動程式碼 UI 測試隨即在 [自動程式碼 UI 測試編輯器] 中顯示。您現在可以檢視及編輯自動程式碼 UI 測試。
在 [UI 動作] 窗格中,選取要移至 UIMap.cs 或 UIMap.vb 檔案的測試方法,以促進自訂程式碼功能,這樣一來,當測試程式碼重新編譯時,就不會覆寫自訂程式碼。
選取 [自動程式碼 UI 測試編輯器] 工具列上的 [移動程式碼] 按鈕。
Microsoft Visual Studio 對話方塊隨即顯示。它會警告此方法將從 UIMap.uitest 檔案移至 UIMap.cs 或 UIMap.vb 檔案,而且您將無法再使用 [自動程式碼 UI 測試編輯器] 編輯此方法。選擇 [是]。
測試方法就會從 UIMap.uitest 檔案移除,不再顯示在 [UI 動作] 窗格中。若要編輯移動的測試檔案,請從方案總管開啟 UIMap.cs 檔案。
在 Visual Studio 工具列上,選取 [儲存]。
測試方法的更新就會儲存在 UIMap.Designer 檔案中。
警告 一旦移動方法,便無法使用 [自動程式碼 UI 測試編輯器] 來編輯方法。您必須使用 [程式碼編輯器] 加入及維護自訂程式碼。
將這個方法從 SimpleAppTest() 重新命名為 ModifiedSimpleAppTest()
將下列 using 陳述式加入至這個檔案:
using Microsoft.VisualStudio.TestTools.UITesting.WpfControls;
將下列 WaitForControlEnabled() 方法加入至先前識別出有問題的那行程式碼前面:
uICheckBoxCheckBox.WaitForControlEnabled(); // Select 'CheckBox' check box uICheckBoxCheckBox.Checked = this.SimpleAppTestParams.UICheckBoxCheckBoxChecked;
在 CodedUITest1.cs 檔案中找出 [CodedUITestMethod] 方法,然後將原始 SimpleAppTest() 方法的參考標記為註解或重新命名,再將它取代為新的 ModifiedSimpleAppTest():
[TestMethod] public void CodedUITestMethod1() { // To generate code for this test, select "Generate Code for Coded UI Test" from the shortcut menu and select one of the menu items. // For more information on generated code, see https://go.microsoft.com/fwlink/?LinkId=179463 //this.UIMap.SimpleAppTest(); this.UIMap.ModifiedSimpleAppTest(); }
在 [建置] 功能表上,選擇 [建置方案]。
以滑鼠右鍵按一下 [CodedUITestMethod] 方法,然後選取 [執行測試]。
這次自動程式碼 UI 測試成功完成測試中的所有步驟,而且 [測試結果] 視窗中顯示 [成功]。
重構 SimpleWPFApp 中的控制項
在 MainWindow.xaml 檔案中,選取設計工具中的按鈕控制項。
在 [屬性] 視窗的頂端,選取 [Button] 旁邊的 [button1] 值,然後將值變更為 buttonA。
在 [建置] 功能表上,選擇 [建置方案]。
選取 [測試] 功能表上的 [視窗],然後選取 [測試檢視]。
在 [測試檢視] 中,選取 [測試名稱] 資料行底下的 [CodedUITestMethod1],然後選取工具列中的 [執行選取範圍]。
測試失敗,因為自動程式碼 UI 測試找不到 UIMap 中原始對應為 button1 的按鈕控制項。重構是以這種方式影響自動程式碼 UI 測試。
在 [測試結果] 視窗中,以滑鼠右鍵按一下失敗的測試,然後選取 [檢視測試結果詳細資料]。
CodedUITestMethod1[Results] 隨即顯示。
在 [錯誤堆疊追蹤] 區段中,選取 [TestProject1.UIMpa.SimpleAppTest()] 旁邊的第一個連結。
UIMap.Designer.cs 檔案隨即開啟。錯誤點反白顯示在程式碼中:
// Choose 'Start' button Mouse.Click(uIStartButton, new Point(27, 10));
請注意,之前在這個程序中的這一行程式碼是使用 UiStartButton,這是重構前的 UIMap 名稱。
若要修正此問題,您可以使用 [自動程式碼 UI 測試產生器] 將重構的控制項加入至 UIMap。您可以將測試的程式碼更新為使用這個程式碼,如下一個程序所示。
對應重構的控制項以及編輯和重新執行自動程式碼 UI 測試
在 CodedUITest1.cs 檔案的 [CodedUITestMethod1()] 方法中,按一下滑鼠右鍵再選取 [產生自動程式碼 UI 測試的程式碼],然後選取 [使用自動程式碼 UI 測試產生器]。
[UIMap - 自動程式碼 UI 測試產生器] 隨即出現。
使用先前建立的桌面捷徑,執行先前建立的 SimpleWPFApp 應用程式。
在 [UIMap - 自動程式碼 UI 測試產生器] 上,將交叉線工具拖曳至 SimpleWPFApp 上的 [Start] 按鈕。
[Start] 按鈕被封入藍色方塊中,而 [自動程式碼 UI 測試產生器] 需幾秒鐘的時間處理所選控制項的資料並顯示控制項屬性。請注意,[AutomationUId] 已命名為 [buttonA]。
在控制項的屬性中選取左上角的箭號,展開 [UI 控制項對應]。請注意,[UIStartButton1] 處於選取狀態。
選取工具列中的 [將控制項加入至 UI 控制項對應]。
視窗底部的狀態會顯示 [選取的控制項已經加入到此 UI 控制項對應] 來確認動作。
選取 [UIMap - 自動程式碼 UI 測試產生器] 上的 [產生程式碼]。
[自動程式碼 UI 測試產生器 - 產生程式碼] 隨即出現,並帶有注意事項,指出不需要新方法,而且只會針對 UI 控制項對應的變更產生程式碼。
選取 [產生]。
關閉 SimpleWPFApp.exe。
關閉 [UIMap - 自動程式碼 UI 測試產生器]。
[UIMap - 自動程式碼 UI 測試產生器] 需幾秒鐘的時間處理 UI 控制項對應變更。
在 [方案總管] 中,開啟 UIMap.Designer.cs 檔案。
在 UIMap.Designer.cs 檔案中,於產生的程式碼類別 UIMainWindow 的建構函式底下,展開 [屬性] 區域。請注意,public WpfButton UIStartButton1 屬性已經加入。
在 UIStartButton1 屬性中,展開 [搜尋準則] 區域。請注意,SearchProperties 已設定為 "buttonA":
public WpfButton UIStartButton1 { get { if ((this.mUIStartButton1 == null)) { this.mUIStartButton1 = new WpfButton(this); #region Search Criteria this.mUIStartButton1.SearchProperties[WpfButton.PropertyNames.AutomationId] = "buttonA"; this.mUIStartButton1.WindowTitles.Add("MainWindow"); #endregion } return this.mUIStartButton1; } }
您現在可以修改自動程式碼 UI 測試來使用新對應的控制項。如先前的程序所述,如果要在自動程式碼 UI 測試中覆寫任何方法或屬性,必須在 UIMap.cs 檔案中這麼做。
在 UIMap.cs 檔案中,加入建構函式並指定 UIStartButton 屬性的 SearchProperties 屬性,以使用值為 "buttonA" 的 AutomationID 屬性:
public UIMap() { this.UIMainWindowWindow.UIStartButton.SearchProperties[WpfButton.PropertyNames.AutomationId] = "buttonA"; }
在 [建置] 功能表上,選擇 [建置方案]。
在 [測試檢視] 中,選取 [測試名稱] 資料行底下的 [CodedUITestMethod1],然後按一下工具列中的 [執行選取範圍]。
這次自動程式碼 UI 測試成功完成測試中的所有步驟。在 [測試結果] 視窗中,您將會看到 [成功] 的狀態。
外部資源
視訊
實作實驗室
MSDN 虛擬實驗室:建立自動程式碼 UI 測試簡介與 Visual Studio 2010
常見問題集
論壇
Visual Studio UI 自動化測試 (包含 CodedUI)