zoukankan      html  css  js  c++  java
  • 自动化测试 Windows 8 应用

    在本博文中,我们将提供自动化 Windows 8 应用测试的一些技巧和技术。请记住自动化测试是一项功能强大的技术,其需要一些初期投资来获得丰厚的回报。本博文中的建议和示例旨在带您入门,而您需要在 此基础上构建并维护您自有的基础结构。如果您要寻求一些轻量级的测试技术,请参阅最近发布的关于使用 Visual Studio 测试应用的博文。

    典型的应用测试自动化工作流程将涉及以下几个步骤:

    • 安装:自动化应用安装。
    • 激活:自动化应用激活。
    • 运行时:当应用运行时自动化应用。
    • 生命周期状态:自动化您的应用的挂起、恢复和终止。
    • 卸载:自动化应用卸载。

    我们来详细介绍一下这些步骤,以及用于各个步骤的自动化工具/技术。

    关于在 Windows RT 上进行测试的注释

    在深入研究自动化主题之前,我们想就在 Windows RT 上测试进行一些简要介绍。您无法构建或移植 x86/64 进程以在 Windows RT 上运行。因此,本博文余下的篇幅中讨论的所有工具和技术均不适用于在 Windows RT 上进行测试。我们建议您使用 Visual Studio 来在 Windows RT 上进行测试

    自动化应用安装

    要测试您的应用,您首先需要在测试机上安装应用。使用 Visual Studio 在本地共享应用包是创建应用包并在测试机上进行安装的建议方法。在该方法中,Visual Studio 将创建一个包含所有相关文件和 PowerShell 脚本的文件夹,其用来安装适当的证书和许可证、相关程序包和应用包本身。您必须手动打包您的应用,但安装是基于 PowerShell 的且可进行自动化处理。以下是具体安装过程。

    第 1 步:

    启用 PowerShell 脚本执行。出于安全原因,默认的 PowerShell 执行策略将限制 PowerShell 脚本的执行,因此您需要替换这一策略。该步骤是手动的,因为其需要进行用户交互。幸运地是,您只需要在每台计算机上执行一次即可。在升级的 PowerShell 窗口中执行该命令,以启用 PowerShell 脚本执行。

    PS C:\> Set-ExecutionPolicy AllSigned
     Powershell_admin
    图 1:启用 PowerShell 脚本执行

    第 2 步:

    将由 Visual Studio 创建的应用包文件夹复制到测试机,并在 PowerShell 窗口中执行 Add-AppDevPackage PowerShell 脚本。使用以下命令:

    PS C:\JSGrid1_1.0.0.0_AnyCPU_Debug_Test> .\Add-AppDevPackage.ps1
    Windows Powershell
    图 2:运行 Add-AppDevPackage 脚本

    第 3 步:

    获取开发人员许可证。该步骤是手动的,因为其需要进行用户交互。但是,您只需在许可证的有效期内针对每台计算机执行一次即可。如果您的测试机已具有开发人员许可证,您可以跳过这一频步骤。

    接受 UAC 提示,并遵从获取开发人员许可证的说明。具体如下面的屏幕截图所示。

    下面的第一个屏幕截图需要您同意安装开发人员许可证的许可条款。如果您要继续,请单击“我同意”。

    Powershell_devlic

    图 3:接受开发人员许可证获取提示

    在“Microsoft 帐户”对话框中,键���您的 Microsoft 帐户。如果您没有 Microsoft 帐户,请单击“注册”来创建帐户。

    msaccount_signin

    图 4:使用 Microsoft 帐户凭据登录

    您将收到已创建开发人员许可证的确认以及许可证的过期日期。

    devlic_approve

    图 5:已成功获取开发人员许可证

    接下来的屏幕截图指示您已成功获得开发人员许可证,并已成功安装应用包。

    PS_packagesuccess

    图 6:安装完成

    自动化应用激活

    您的应用包现已在测试机上成功安装,现在您可以启动该应用。您可以使用 IApplicationActivationManager 接口来自动化应用激活。该 API 作为 Windows SDK 的一部分提供,在默认情况下,Visual Studio 2012 会安装 Windows SDK。使用 IApplicationActivationManager::ActivateApplication 方法启动您的应用。以下代码段显示了该方法的使用。

    #include "stdafx.h"
    #include <shlobj.h>
    #include <stdio.h>
    #include <shobjidl.h>
    #include <objbase.h>
    #include <atlbase.h>
    #include <string>

    /*++

    Routine Description:

    This routine launches your app using IApplicationActivationManager.

    Arguments:

    strAppUserModelID - AppUserModelID of the app to launch.
    pdwProcessId - Output argument that receives the process id of the launched app.

    Return value:

    HRESULT indicating success/failure

    --*/
    HRESULT LaunchApp(const std::wstring& strAppUserModelId, PDWORD pdwProcessId)
    {
    CComPtr<IApplicationActivationManager> spAppActivationManager;
    HRESULT hrResult = E_INVALIDARG;
    if (!strAppUserModelId.empty())
    {
    // Instantiate IApplicationActivationManager
    hrResult = CoCreateInstance(CLSID_ApplicationActivationManager, NULL, CLSCTX_LOCAL_SERVER, IID_IApplicationActivationManager, (LPVOID*)&spAppActivationManager);

    if (SUCCEEDED(hrResult))
    {
    // This call ensures that the app is launched as the foreground window
    hrResult = CoAllowSetForegroundWindow(spAppActivationManager, NULL);

    // Launch the app
    if (SUCCEEDED(hrResult))
    {
    hrResult = spAppActivationManager->ActivateApplication(strAppUserModelId.c_str(), NULL, AO_NONE, pdwProcessId);
    }
    }
    }

    return hrResult;
    }

    int _tmain(int argc, _TCHAR* argv[])
    {
    HRESULT hrResult = S_OK;
    if (SUCCEEDED(CoInitializeEx(NULL, COINIT_APARTMENTTHREADED)))
    {
    if (argc == 2)
    {
    DWORD dwProcessId = 0;
    ++argv;
    hrResult = LaunchApp(*argv, &dwProcessId);
    }
    else
    {
    hrResult = E_INVALIDARG;
    }

    CoUninitialize();
    }

    return hrResult;
    }

    您可以编译该代码段,并通过如下方式对其加以利用:

    C:\>Win8AppLaunch.exe Microsoft.BingNews_8wekyb3d8bbwe!AppexNews

    在该代码段中,对 CoAllowSetForegroundWindow 的调用是最关键的。如果不执行该调用,应用将启动而不会被置于前台。根据经验,这已阻碍许多尝试编写启动工具的开发人员。

    最后是关于 AppUserModelId 的简要介绍。在该方法中,启动您的应用需要输入应用的 AppUserModelId。AppUserModelId 可用作您的应用的唯一标识符。要对其进行检索,我们建议您使用 PowerShell。以下是显示您如何在自己的计算机上检索所有已安装应用的 AppUserModelId 的 PowerShell 脚本。

    $installedapps = get-AppxPackage
    foreach ($app in $installedapps)
    {
    foreach ($id in (Get-AppxPackageManifest $app).package.applications.application.id)
    {
    $app.packagefamilyname + "!" + $id
    }
    }

    您还可以使用 IAppxManifestReader 来列举应用包中的应用,并使用 IAppxManifestApplication::GetAppUserModelId 方法获得 AppUserModelId。但是,如果您优先考虑的是您测试的单一应用,则使用注册表要远比编写读取应用程序清单的工具容易。

    自动化应用的核心功能

    您的应用现已在测试机上成功安装,并且您的自动化可以启动该应用。接下来的步骤将涉及自动化您的应用的核心功能测试。您可以结合使用单元测试并使用 UI 自动化通过应用的用户界面来自动化应用来完成这一任务。

    单元测试和 UI 自动化是两项互补性的技术,同时使用时可扩大应用的测试范围,并提高应用的质量。单元测试允许您自动化应用中的核心业务逻辑。UI 自动化测试可通过模拟应用的用户界面使用来允许您验证应用的功能。结合使用这两种方法可使您的应用获得更广泛的测试覆盖范围。

    我们来看一下其中每种方法的工具和技术。

    单元测试

    单元测试是验证应用的核心功能的一项强大技术。Visual Studio 2012 支持为使用 C# 或 C++ 编写的应用构建单元测试。有关通过 Visual Studio 2012 创建和运行单元测试的详细信息,请参阅创建和运行单元测试。如果您已熟悉其他单元测试框架,您也可以继续使用这些单元测试来对 Windows 应用商店应用进行测试。

    UI 自动化

    单元测试对于测试应用的内部工作非常有效,但它无法测试应用的用户界面。我们推荐使用 UI 自动化 (UIA) 通过用户界面来验证应用的功能。

    在 Windows 8 安全模型中,应用不具备 UI 自动化客户端所需的特权。不过,您可以编写一个桌面应用作为自动化客户端,并以您的应用为目标。为此,您的桌面自动化客户端应用需要建立 UIAccess 权限,如 UI 自动化安全概述中所述。

    Windows SDK 包含一些工具,可以作为 UI 自动化客户端的典型示例:Inspect.exe 和 AccEvent.exe。利用 Inspect,可以检查两类应用的 UI 自动化树。AccEvent 可以侦听 UIA 事件。在安装有 Windows SDK 的计算机上,这些工具通常位于 %ProgramFiles(x86)%\Windows Kits\8.0\bin\<architecture> 下。下面显示了这两个工具的使用示例:

    inspect.exe

    图 7:对 Bing News 运行 Inspect 工具

    accevent_tool

    图 8:对 Bing Sports 运行 AccEvent 工具

    与这些工具所使用的方法类似,您可以使用 UIA 编写桌面客户端应用来自动化您的应用。要了解如何构建 UIA 客户端,请参阅使用 C++ 和 C# 构建 UI 自动化客户端应用博文。此博文讲述了传统的 UI 自动化流程,但相同的技术同样适用于任何应用。

    UI 自动化文档内容客户端示例演示了如何使用 UIA 控制模式从目标应用的窗口来检索各种类型的内容,例如,标题、注释或当前所选内容。触控注入示例演示了如何使用触控注入 API 来模拟触控行为以验证您的应用。

    如上文所述,单元测试和 UI 自动化是两项互补性的技术,可以用来自动化应用中的核心业务逻辑以及通过用户界面执行的功能。结合使用这两项技术可以调试您的应用。

    自动化应用的生命周期状态

    管理应用程序生命周期博文中所述,应用可以在不同运行时状态间切换。从测试的角度而言,在所有这些状态下验证您的应用至关重要。使用 Windows 调试工具附带的 PLMDebug 工具可以自动切换这些状态,这是一个现成的命令行工具,可以用来自动切换应用的生命周期状态。

    如果 PLMDebug 无法满足您的需求,可以使用 IPackageDebugSettings 接口实现自己的工具,用于更改应用的生命周期状态。该 API 作为 Windows SDK 的一部分提供,在默认情况下,Visual Studio 会安装 Windows SDK。以下代码演示了如何使用 IPackageDebugSettings API 更改应用的生命周期状态,以验证您的应用在状态切换过程中能够按预期方式工作。

    #include "stdafx.h"
    #include <stdio.h>
    #include <shobjidl.h>
    #include <objbase.h>
    #include <atlbase.h>
    #include <string>

    /*++

    Routine Description:

    This routine changes the lifecycle state of a Windows Store app depending on the input argument.

    Arguments:

    strPackageFullName - Package Full Name of the Windows Store app
    strOperation - Operation to take (/enabledebug, /suspend, /resume, /terminate, /cleanTerminate, /disabledebug)

    Return Value:

    HRESULT indicating success/failure

    --*/
    HRESULT ChangeLifecycleState(const std::wstring& strPackageFullName, const std::wstring& strOperation)
    {
    CComPtr<IPackageDebugSettings> spPackageDebugSettings;
    HRESULT hrResult = E_INVALIDARG;

    if (!strPackageFullName.empty() && !strOperation.empty())
    {
    // Instantiate IPackageDebugSettings
    hrResult = CoCreateInstance(CLSID_PackageDebugSettings, NULL, CLSCTX_INPROC_SERVER, IID_PPV_ARGS(&spPackageDebugSettings));

    // Depending on the operation specified as the command line arg, change the lifecycle state of the app
    if (SUCCEEDED(hrResult))
    {
    if (_wcsicmp(strOperation.c_str(), L"/enableDebug") == 0)
    {
    // Increment debug ref count on the app package - you must do this before you can suspend/resume/terminate
    hrResult = spPackageDebugSettings->EnableDebugging(strPackageFullName.c_str(), NULL, NULL);
    }
    else if (_wcsicmp(strOperation.c_str(), L"/suspend") == 0)
    {
    // Asynchronously suspend the app
    hrResult = spPackageDebugSettings->Suspend(strPackageFullName.c_str());
    }
    else if (_wcsicmp(strOperation.c_str(), L"/resume") == 0)
    {
    // Resume the app
    hrResult = spPackageDebugSettings->Resume(strPackageFullName.c_str());
    }
    else if (_wcsicmp(strOperation.c_str(), L"/terminate") == 0)
    {
    // Terminate the app
    hrResult = spPackageDebugSettings->TerminateAllProcesses(strPackageFullName.c_str());
    }
    else if (_wcsicmp(strOperation.c_str(), L"/cleanTerminate") == 0)
    {
    // Clean terminate the app - suspend, then terminate
    hrResult = spPackageDebugSettings->StartServicing(strPackageFullName.c_str());
    if (SUCCEEDED(hrResult))
    {
    hrResult = spPackageDebugSettings->StopServicing(strPackageFullName.c_str());
    }
    }
    else if (_wcsicmp(strOperation.c_str(), L"/disableDebug") == 0)
    {
    // Decrement debug ref count on the app package
    hrResult = spPackageDebugSettings->DisableDebugging(strPackageFullName.c_str());
    }
    else
    {
    hrResult = E_INVALIDARG;
    }
    }
    }

    return hrResult;
    }

    int _tmain(int argc, _TCHAR* argv[])
    {
    HRESULT hrResult = S_OK;
    if (SUCCEEDED(CoInitializeEx(NULL, COINIT_APARTMENTTHREADED)))
    {
    if (argc == 3)
    {
    std::wstring strOperation(argv[1]);
    std::wstring strPackageFullName(argv[2]);
    hrResult = ChangeLifecycleState(strPackageFullName, strOperation);
    }
    else
    {
    hrResult = E_INVALIDARG;
    }

    CoUninitialize();
    }

    return hrResult;
    }
    如何将此代码段编译为 LifecycleManager.exe,下面显示了如何使用该程序。
    C:\>Win8AppLifecycleManager.exe /enableDebug Microsoft.BingNews_1.2.0.98_x64__8wekyb3d8bbwe

    C:\> Win8AppLifecycleManager.exe /suspend Microsoft.BingNews_1.2.0.98_x64__8wekyb3d8bbwe

    C:\> Win8AppLifecycleManager.exe /resume Microsoft.BingNews_1.2.0.98_x64__8wekyb3d8bbwe

    C:\> Win8AppLifecycleManager.exe /terminate Microsoft.BingNews_1.2.0.98_x64__8wekyb3d8bbwe

    C:\> Win8AppLifecycleManager.exe /cleanTerminate Microsoft.BingNews_1.2.0.98_x64__8wekyb3d8bbwe

    C:\> Win8AppLifecycleManager.exe /disableDebug Microsoft.BingNews_1.2.0.98_x64__8wekyb3d8bbwe
     

    最后是关于 PackageFullName 的简要介绍。我们介绍的用来管理生命周期状态的所有方法均要求使用 PackageFullName 作为输入参数,通过该参数来标识应用。要检索 PackageFullName,推荐您使用下例所示的 Get-AppxPackage PowerShell cmdlet(对输出进行了整理以方便阅读)。

    PS C:\> Get-AppxPackage

    Name : Microsoft.BingNews
    Publisher : CN=Microsoft Corporation, O=Microsoft Corporation, L=Redmond, S=Washington, C=US
    Architecture : X64
    ResourceId :
    Version : 1.2.0.98
    PackageFullName : Microsoft.BingNews_1.2.0.98_x64__8wekyb3d8bbwe ←
    InstallLocation : C:\Program Files\WindowsApps\Microsoft.BingNews_1.2.0.98_x64__8wekyb3d8bbwe
    IsFramework : False
    PackageFamilyName : Microsoft.BingNews_8wekyb3d8bbwe
    PublisherId : 8wekyb3d8bbwe

    自动化应用卸载

    要卸载应用,推荐您使用 PowerShell cmdlets,具体来说,使用 Remove-AppxPackage。如下例所示(对输出进行了整理以方便阅读)。

    PS C:\> Get-AppxPackage

    Name : Microsoft.SDKSamples.ListViewEssentials.JS
    Publisher : CN=Microsoft Corporation, O=Microsoft Corporation, L=Redmond, S=Washington, C=US
    Architecture : Neutral
    ResourceId :
    Version : 1.0.0.0
    PackageFullName : Microsoft.SDKSamples.ListViewEssentials.JS_1.0.0.0_neutral__8wekyb3d8bbwe ←
    InstallLocation : C:\Users\user1\Downloads\Samples\Controls_ListViewBasic\JS\bin\Debug\AppX
    IsFramework : False
    PackageFamilyName : Microsoft.SDKSamples.ListViewEssentials.JS_8wekyb3d8bbwe
    PublisherId : 8wekyb3d8bbwe

    PS C:\> Remove-AppxPackage Microsoft.SDKSamples.ListViewEssentials.JS_1.0.0.0_neutral__8wekyb3d8bbwe

    总结

    在本博文中,我们介绍了自动化应用测试的一些技巧、工具和技术。自动化测试是提高应用验证水平的经济高效的方式,可以确保应用的质量不会下降。也就 是说,在验证过程中,手动测试同样具有重要作用。在应用验证过程中,手动测试可以提供更强的人工干预。因此,结合使用自动化测试和手动测试可以对您的应用 进行全面测试。

    -- Windows 首席测试主管 Ashwin Needamangala

    在此特别感谢 Mete Goktepe、J. Kalyana Sundaram、Ben Betz、Will Wei、Chris Edmonds、Craig Campbell 和 Jake Sabulsky,感谢他们为本文的撰写提供帮助和支持。

  • 相关阅读:
    checkbox的checked事件的javascript使用方法
    JSTL标签API(c)的使用
    radios控件的使用
    验证方法判斷input是否为空
    软件课设Day5
    软件课设Day4
    软件课设Day3
    软件课设Day2
    软件课设Day1
    2019/08/23最新进展
  • 原文地址:https://www.cnblogs.com/shihao/p/2687582.html
Copyright © 2011-2022 走看看