在本演练中,您将创建一个简单的 Windows Presentation Foundation (WPF) 应用程序来演示如何创建、编辑和维护编码的 UI 测试。本演练为更正由各种计时问题和控件重构中断的测试提供了解决方案。
系统必备
本演练需要:
- 最终的 Visual Studio 或 Visual Studio premium。
创建一个简单的 WPF 应用程序
在**“文件”菜单上指向“新建”,然后选择“项目”**。
此时将出现“新建项目”对话框。
在 已安装 窗格中,展开 Visual C#,然后选择 窗口。
在中间窗格之上,验证是否将目标框架下拉列表设置为**“.NET Framework 4.5”**。
在中间窗格中,选择**“WPF 应用程序”**模板。
在**“名称”**文本框中,键入 SimpleWPFApp。
选择要用于保存项目的文件夹。在**“位置”**文本框中,键入文件夹的名称。
选择**“确定”**。
用于 Visual Studio 的 WPF 设计器将打开,并显示项目的主窗口。
如果当前未打开工具箱,请将其打开。选择 查看 菜单,然后选择 工具箱。
在**“所有 WPF 控件”部分,将一个“Button”、“CheckBox”和“ProgressBar”**控件拖动到设计图面的主窗口中。
选择 Button 控件。在“属性”窗口中,将**“Content”属性的值由“Button”**更改为“Start”。
选择 ProgressBar 控件。在“属性”窗口中,将**“Maximum”属性的值由“100”更改为“1000”**。
选择 Checkbox 控件。在“属性”窗口中,清除**“IsEnabled”**属性。
双击按钮控件添加选择事件。
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 测试项目 模板。
选择**“确定”**。
在解决方案资源管理器中,新的编码 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 测试生成器"中,选择 生成代码。
在"方法名称"并选择 添加并生成。几秒后,编码的 UI 测试将出现,并且会添加到“解决方案”中。
关闭“UIMap – 编码的 UI 测试生成器”。
CodedUITest1.cs 文件将出现在代码编辑器中。
运行编码的 UI 测试
在 CodedUITest1.cs 文件中,找到**“CodedUITestMethod”方法,右击并选择“运行测试”**。
当编码的 UI 测试运行时,SimpleWPFApp 将可见。它会执行您在前面的过程中执行的步骤。但是,当测试试图选中 CheckBox 控件对应的复选框时,“测试结果”窗口将显示测试未通过。原因是测试试图选中该复选框,但不知道 CheckBox 控件已被禁用,直至进度栏 100% 完成为止。通过可用于编码的 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 文件中删除对原始方法的引用,并将其替换为重命名的方法名称。
在解决方案资源管理器中,找到 UIMap.uitest 编码的 UI 测试项目。
打开 UIMap.uitest 的快捷菜单中选择 打开。
编码的 UI 测试编辑器中将显示编码的 UI 测试。此时您可以查看并编辑编码的 UI 测试。
在**“UI 操作”**窗格中,选择要移动到 UIMap.cs 或 UIMap.vb 文件的测试方法,以便使用在重新编译测试代码时不会重写的自定义代码功能。
选择在编码的 UI 移动代码 测试编辑器工具栏中的按钮。
将显示一个 Microsoft Visual Studio 对话框。该对话框警告您方法将从 UIMap.uitest 文件移动到 UIMap.cs 文件,并且您不再能够编辑该方法使用编码的 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。
在**“生成”菜单上,选择“生成解决方案”**。
在 测试 菜单,选择" 窗口 然后选择 测试视图。
在中,在 测试名称 列下的 SELECT 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
FAQ
论坛
Visual Studio UI 自动测试 (包括 CodedUI)