【问题标题】:TestNG Automation Framework running tests individually, locallyTestNG 自动化框架在本地单独运行测试
【发布时间】:2018-02-15 12:39:47
【问题描述】:

我是 TestNG 的初学者。我目前在一家公司工作,他们有一个本土的 api 自动化框架。我习惯于在本地和使用 Cucumber 时单独运行我的测试用例。然而,在这个框架中,事情是非常紧密耦合的。让我简要介绍一下框架的不同方面:

测试数据管理: 测试数据通过属性文件读取。所有测试用例数据都使用每个 api 模块的键值列在属性中。键的编号方式是按测试用例类型和附加的计数器。比如:

example.properties

.....
.....
    getTestCase38=TC_ID_38
    getDescription38= Description_38
    getUserID38=<some value>
    getUserType38=<some value>
    expectedUserType38=<some value>

    getTestCase39=TC_ID_39
    getDescription39= Description_39
    getUserID39=<some value>
    getUserType39=<some value>
    expectedUserType39=<some value>

    postTestCase1=TC_ID_1
    postDescription1= Description_1
    postUserID1=<some value>
    postUserType1=<some value>
    expectedUserType1=<some value>
...
...

测试数据流: 从属性文件中读取数据。一个属性文件映射到一个 TestNG 类。 TestNG 类中这些方法的命名约定如下:

public class ModuleA extends ModuleACommon{    

int getcount = 0;
int postcount = 0;

    @Test(priority=20)
    public void testMoudleAGetPositive38(){
     callMethodToReadData(getcount++);
     ....
    }   

    @Test(priority=21)
    public void testModuleAGetPositive39(){
     callMethodToReadData(getcount++);
     ....
     ....
    } 
    ......
    ......

    @Test(priority=30)
    public void testModuleAPostPositive1(){
     callMethodToReadData(postcount++);
     ....
     ....
    }   
   ......
   ......
}

请注意,当调用callMethodToReadData 时,计数会增加,并用于构建密钥以访问属性文件中的测试数据。测试用例按顺序设置为优先级,这样可以确保构造正确的键。这很痛苦,因为如果我想按照这种模式添加一个新的测试用例。假设我想添加一个测试用例并为其分配优先级 21,那么我将不得不调整 21 之后的所有测试方法的优先级,包括第 21 个优先级测试用例。

短期: 我试图找到一种最简单的方法来单独运行一个测试。有一些肮脏的方法可以做到这一点。例如,我可以只注释掉其他测试用例并重新分配适当的计数值,但这太低效了。

长期: 从长远来看,我很想听听意见和建议以改善这一点。我自己对长期改进有一些想法,但是我希望从这里获得更多有见地的建议。

另外,如果有任何技巧可以解决添加测试用例而不需要重新组织优先级的问题,请告诉我(我有一个我已经实施的解决方案,我只使用一个更具描述性的唯一键实际测试用例)。

【问题讨论】:

    标签: java testing automated-tests testng integration


    【解决方案1】:

    合并使用这种方法可以看到的一些问题:

    1. 不支持并行执行:构建测试的方式,如果我尝试并行运行它们,整个系统将崩溃,因为从数据源获取数据的方法(在您的情况下为属性文件)依赖于类中的非线程安全数据成员。
    2. 正如您已经说过的,无法轻松添加新测试,也无法灵活地将它们作为独立测试运行。
    3. 测试重新排序

    为了能够独立运行测试是能够更改您的密钥。您当前的键依赖于一些 int 值,需要将其传递给数据源,以便您可以检索它的属性。

    我建议您将其更改为开始作为 @Test 的方法名称。既然您说对于每个测试类,您都将拥有一个属性文件,并且由于 Java 不允许您定义两个具有相同名称的方法(当然方法重载可以让您这样做,但是因为我们正在谈论 @987654324 @ 方法,我们可以方便地忽略该部分),如果您让它们依赖于方法名称,您的键仍然是唯一的。现在您也不需要显式引用方法名称。在您的@Test 方法中,如果您调用了callMethodToReadData(),那么您的callMethodToReadData() 只需调用org.testng.Reporter.getCurrentTestResult().getMethod().getMethodName() 即可轻松检索当前正在运行的@Test 方法的名称(请记住,TestNG 确保存在有效的ITestResult 对象当您从@Test 方法中查询线程局部变量Reporter.getCurrentTestResult 时)

    现在这将使您摆脱对计数器的依赖,从而形成您的密钥。您的属性文件更具可读性,因为键现在代表方法名称,因此数据属于哪个测试方法更加清晰。

    您也不必在添加新测试时更改优先级(当然,如果您真的想更改测试的顺序,则需要调整优先级,因为这就是优先级的用途......@987654333 @)

    您甚至可以通过构建org.testng.IAnnotationTransformer 的实现来获得更多幻想,其中您可以根据您可以读取的JVM 参数随意启用/禁用@Test 方法。这样一来,您就可以随意运行任何@Test 方法。如果您使用 maven 作为构建工具,那么您真的不需要转换器,因为 maven surefire 插件本身就可以做到这一点。

    从长远来看,我相信你需要开始关注dataprovider 甚至工厂。您可能还想摆脱属性的概念,转而使用复杂的东西,例如 JSON/YAML/XML,或者只是退回到 excel 电子表格,因为在 excel 电子表格中,您可以通过可视化每个工作表作为表格,然后让一个表格使用键引用另一个表格。然后,您可以构建一个复杂的 excel 数据提供程序,它能够从电子表格中提取数据并填充 POJO(您需要创建一个,它对您的电子表格数据行进行建模)。这就是我们最终构建和开源的内容,作为构建 SeLion 的一部分。想了解更多我说的excel数据提供者,可以参考here

    【讨论】:

    • 感谢您提出如此深刻的想法。我肯定会将这些应用到我未来的实现中。但是,如果您详细说明 JSON/YAML/XML 与属性文件的用法,将会很有帮助。我确实有使用 JSON 作为我的测试数据加载技术的经验,但是在使用属性文件后,我无法区分两者的用处。
    • @sophist_pt - JSON/YAML/XML 都可以让您表示复杂的对象,但属性文件不允许您这样做。在属性中,一切都是键/值对。但是,如果必须将值可视化为另一组键/值对,它在属性世界中很快就会变得复杂。但是您可以使用 JSON/Yaml/XML 轻松地做到这一点。无论如何,我认为如果您能帮助将其作为单独的查询发布会很好。如果它回答了您的问题,也请帮助接受我的回答。
    • 复杂对象,是的,我同意!但是,另一组键/值对我认为通过属性文件同样可能,因为它只是从属性文件读取时将 json 字符串转换为 json 对象的问题。
    • @sophist_pt - 当你需要依赖解析逻辑来理解你的属性文件时,你需要停止使用它。属性仅用作简单的键/值对。对于更复杂的事情,您应该使用相关的数据表示机制,例如 json/xml/yaml。属性绝对不是我们想要的数据表示机制。
    • 但是,即使您使用 json,您也需要构建一些额外的 json 解析工具来进行必要的转换以供使用。那么,就一个与另一个的附加逻辑实现而言,它有何不同?
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2017-07-10
    • 1970-01-01
    • 2012-02-25
    • 1970-01-01
    • 2016-07-09
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多