【问题标题】:@BeforeMethod/@AfterMethod(onlyForGroups) methods did not execute, if a test method belonging to this group is executed@BeforeMethod/@AfterMethod(onlyForGroups) 方法没有执行,如果属于该组的测试方法被执行
【发布时间】:2021-02-18 15:39:01
【问题描述】:

我正在使用属于特定组的测试方法运行一个测试套件。

以下是 Selenium 代码:​​

public class BaseClass
{

    @BeforeMethod(onlyForGroups = {"P1"})
    public void bmeth1()
    {
        System.out.println("Before Method1 called");
    }

    @BeforeMethod(onlyForGroups = {"P2"})
    public void bmeth2()
    {
        System.out.println("Before Method2 called");
    }

    @BeforeMethod(onlyForGroups = {"P3"})
    public void bmeth3()
    {
        System.out.println("Before Method3 called");
    }

    @AfterMethod(onlyForGroups = {"P1"})
    public void ameth1()
    {
        System.out.println("After Method1 called");
    }

    @AfterMethod(onlyForGroups = {"P2"})
    public void ameth2()
    {
        System.out.println("After Method2 called");
    }

    @AfterMethod(onlyForGroups = {"P3"})
    public void ameth3()
    {
        System.out.println("After Method3 called");
    }

}

public class TC_003 extends BaseClass
{

    @Test(groups = {"P1"})
    public void tCase6()
    {
        System.out.println("Inside testcase 6");
    }

    @Test(groups = {"P2"})
    public void tCase7()
    {
        System.out.println("Inside testcase 7");
    }

    @Test(groups = {"P3"})
    public void tCase8()
    {
        System.out.println("Inside testcase 8");
    }

}

下面是 testng.xml 文件:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE suite SYSTEM "https://testng.org/testng-1.0.dtd">
<suite name="Suite" verbose="10">
<test name="Test1">
    <groups>
        <run>
            <include name=".*"/>
        </run>
    </groups>
    <classes>
        <class name="testing.TC_003"/>
    </classes>
</test>
</suite>

实际输出:

Inside testcase 6
Inside testcase 7
Inside testcase 8

预期输出:

Before Method1 called
Inside testcase 6
After Method1 called
Before Method2 called
Inside testcase 7
After Method2 called
Before Method3 called
Inside testcase 8
After Method3 called

测试方法已执行,但@BeforeMethod/@AfterMethod 没有执行。仅当我们在 testng.xml 文件中包含某些组时才会出现此问题。但是如果我们在 testng.xml 文件中排除某些组或不使用组标签,那么它们就会被执行。

按照here 的建议,当前的解决方法是使用 alwaysRun=true 标志和 onlyForGroups 标志。但是如果我们应用这个变通方法,并且如果前面/父配置方法中有任何 SkipException,那么即使要跳过测试方法,也会强制执行 @BeforeMethod/@AfterMethod 方法。当前面的/父配置方法失败时,记录了类似的问题here

【问题讨论】:

    标签: java selenium selenium-webdriver testng


    【解决方案1】:

    这是一个有趣的观察,如果您将 onlyforgroups 更改为组,那么一切正常:

    但是当你的 testng.xml 中包含多个组时,那么在提到的组中的所有之前和之后的方法都会在每个测试方法之前执行。因此,为了避免这种情况,您必须将组和仅组混合在一起

    解释:

    如果您没有在 testng xml 中指定组,那么所有方法都会被调用。但是如果你提到组,那么只有该特定组中的方法才会被执行。

    这是因为如果您阅读组的定义:

    https://testng.org/doc/documentation-main.html

    groups 该类/方法所属的组列表。

    因此,如果您不提及组或始终运行 true,则不会调用该方法,因此您不会调用 before 和 after 方法,因为它们不在任何组中

    解决方法:

    您可以将两者混合为:

    package driversetup;
    
    import org.testng.annotations.AfterMethod;
    import org.testng.annotations.BeforeMethod;
    
    
    
    public class TestBaseClass  {
        
    
        @BeforeMethod(onlyForGroups = {"P1"},groups = {"P1"})
        public void bmeth1()
        {
            System.out.println("Before Method1 called");
        }
    
        @BeforeMethod(onlyForGroups = {"P2"},groups = {"P2"})
        public void bmeth2()
        {
            System.out.println("Before Method2 called");
        }
    
        @BeforeMethod(onlyForGroups = {"P3"},groups = {"P3"})
        public void bmeth3()
        {
            System.out.println("Before Method3 called");
        }
    
        @AfterMethod(onlyForGroups = {"P1"},groups = {"P1"})
        public void ameth1()
        {
            System.out.println("After Method1 called");
        }
    
        @AfterMethod(onlyForGroups = {"P2"},groups = {"P2"})
        public void ameth2()
        {
            System.out.println("After Method2 called");
        }
    
        @AfterMethod(onlyForGroups = {"P3"},groups = {"P3"})
        public void ameth3()
        {
            System.out.println("After Method3 called");
        }
        
    
    }
    

    或启用始终运行 true

    package driversetup;
    
    import org.testng.annotations.AfterMethod;
    import org.testng.annotations.BeforeMethod;
    
    
    
    public class TestBaseClass {
        
    
        @BeforeMethod(onlyForGroups = {"P1"},alwaysRun = true)
        public void bmeth1()
        {
            System.out.println("Before Method1 called");
        }
    
        @BeforeMethod(onlyForGroups = {"P2"},alwaysRun = true)
        public void bmeth2()
        {
            System.out.println("Before Method2 called");
        }
    
        @BeforeMethod(onlyForGroups = {"P3"},alwaysRun = true)
        public void bmeth3()
        {
            System.out.println("Before Method3 called");
        }
    
        @AfterMethod(onlyForGroups = {"P1"},alwaysRun = true)
        public void ameth1()
        {
            System.out.println("After Method1 called");
        }
    
        @AfterMethod(onlyForGroups = {"P2"},alwaysRun = true)
        public void ameth2()
        {
            System.out.println("After Method2 called");
        }
    
        @AfterMethod(onlyForGroups = {"P3"},alwaysRun = true)
        public void ameth3()
        {
            System.out.println("After Method3 called");
        }
        
    
    }
    

    这可确保调用 before 和 after 方法,但仅针对正确的 @test 方法执行

    【讨论】:

    • 我观察到,如果我们使用第二种解决方法,即@BeforeMethod/@AfterMethod(onlyForGroups = {"P1"}, alwaysRun=true),那么它会强制执行@BeforeMethod/@AfterMethod,即使它是前面/父配置方法并且后续测试方法有已被跳过,这类似于记录的现有问题 here。所以,我觉得我们应该删除第二种解决方法。让我知道你的看法。
    • 让我检查并返回
    • @SandeshSawant 你是如何跳过这些方法的?
    • 在配置方法@BeforeMethod中使用throw new SkipException()
    【解决方案2】:

    我不确定这个正则表达式是否适用于所有组,所以请尝试删除这些行:

    <groups>
        <run>
            <include name=".*"/>
        </run>
    </groups>
    

    【讨论】:

    • 如果我删除组标签或使用排除,那么如原帖所述,达到预期的结果。但是,如果我们只想包括某些组或所有组,则会出现上述问题。目前,我找到了一种解决方法,我已将其发布为该问题的答案。
    【解决方案3】:

    以下是原帖中提到的问题的解决方法:

    如果我们只想执行某些组,那么我们可以排除那些我们不想执行的组,而不是对我们想要执行的组使用包含。
    同样,如果我们要执行所有组,那么不要使用&lt;include name=".*"/&gt;,而是使用 exclude 并提供一些在您的测试套件中不存在的组名称,例如&lt;exclude name="unknown"/&gt;&lt;exclude name=""/&gt;
    但请注意,在使用上述解决方法时,它还将包括并运行所有不属于任何组的测试。因此,我们必须通过为所有我们认为不属于任何特定组的测试和配置方法分配一个默认组来应用另一种解决方法。

    因此,如果我们应用上述解决方法,那么我们不必应用原始帖子中提到的解决方法,即我们不必使用alwaysRun=true 标志和onlyForGroups。也就是说,我们可以使用@BeforeMethod/@AfterMethod(onlyForGroups = {"P2"}) 而不是@BeforeMethod/@AfterMethod(onlyForGroups = {"P2"}, alwaysRun=true)

    请避免这个答案,因为我对组和 onlyForGroups 标志以及如何以及何时使用这些标志并不十分清楚。因此,我建议使用 PDHide 提供的简单解决方案,因为它更清楚地解释了组和 onlyForGroups 标志之间的区别以及如何以及何时使用它们。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2017-11-27
      • 2022-11-12
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多