【问题标题】:Is there a way to get the class variables into the testNG before method of super class有没有办法在超类的方法之前将类变量放入 testNG
【发布时间】:2021-07-26 17:19:48
【问题描述】:

我在 class1 中有 @test 方法,在超类中有 @before 方法。我想在@before方法中访问class1中声明的类变量。

【问题讨论】:

    标签: testng testng-annotation-test


    【解决方案1】:

    没有。这是违反继承规则的。超类是父类,你问题中提到的class1是子类。

    子类可以访问父类的属性,但反之亦然。 Here 是一个类似的问题,有更多解释。

    【讨论】:

      【解决方案2】:

      术语“类变量”用于表示静态变量。我假设您打算讨论“实例变量”的使用。如果要在父类中使用实例变量,那么理想情况下它应该是父类的实例变量。

      如果您真的想在父类中使用子类的“类变量”(或静态变量),那么它是可能的(如果它具有相关的访问修饰符)

      【讨论】:

        【解决方案3】:

        可以使用反射访问实例变量和类变量。虽然这不是推荐的方式(如 cmets shared 所述)。

        您可以使用 google 的 guice 库为 @Before@After 挂钩在 testng 中使用已经实现的依赖注入。分享一个相同的例子:

        
        public class Test extends BaseTest {
        
            String stringOne = "INTER";
            static final String stringTwo = "MISSION";
        
            @Test(testName = "Sample Test")
            private void reflection_test() {
                System.out.println("-----INSIDE THE SUB CLASS-----");
                System.out.println(stringOne + stringTwo);
            }
        
        }
        

        现在在基类中的@Before 中,我们将ITestResult 作为参数添加到方法中(您可以阅读有关testng 的依赖注入here)。

        现在使用ITestResult参数,我们可以得到测试类,然后可以使用Java反射来获取实例化的类对象、字段、方法等。检查以下示例:

        public class BaseTest {
        
            @BeforeMethod(alwaysRun = true)
            public void init(ITestResult result) throws IllegalAccessException {
                Class clazz = result.getTestClass().getRealClass();
                System.out.println("-----THIS IS FROM THE PARENT CLASS-----");
                for (Field f : clazz.getDeclaredFields()) {
                    System.out.println("Variable Value : " + f.get(this));
                }
                System.out.println();
            }
        
        }
        

        在执行测试时,我们将收到以下输出:

        -----THIS IS FROM THE PARENT CLASS-----
        Variable Value : INTER
        Variable Value : MISSION
        
        -----INSIDE THE SUB CLASS-----
        INTERMISSION
        

        【讨论】:

        • 这真的是运行这段代码后的输出吗?
        • 这里使用作为运行测试的一部分创建的子对象检索子类的字段。没有违反继承规则。此外,您不需要反射来实现这一点。只是一个简单的if(this instanceof ChildTest) System.out.println(((ChildTest) this).stringOne);。反射仅在需要所有字段时才有用,以便您可以循环执行。从问题来看,似乎只需要几个字段。
        • 嘿@GauthamM,是的,上面的输出来自执行代码。由 OP 决定他需要多少字段来适应他的原因(这可以满足使用反射或基于实例类型的简单类型转换)。根据您的评论,我进行了编辑,删除了答案中的继承使用。
        • 请注意,这个使用ITestResult的解决方案不适用于像6.8这样的旧版本的testNG。因为在这样的版本中,ITestResult 中的属性在到达 BeforeMethod 时会为 null,这会导致 beforeMethod 失败。这已在较新的版本中得到修复。所以我建议接收Method 作为参数,然后使用clazz = method.getDeclaringClass()。或者你可以删除所有参数,只使用clazz = this.getClass();
        猜你喜欢
        • 2011-11-13
        • 2023-03-29
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2021-05-15
        • 1970-01-01
        • 2020-01-12
        • 1970-01-01
        相关资源
        最近更新 更多