【问题标题】:Geb Reporter / Extension to retrieve Test StatusGeb Reporter / Extension 以检索测试状态
【发布时间】:2013-02-28 14:33:15
【问题描述】:

我正在尝试使用geb 替换一些自定义的 java selenium 扩展。当我尝试在云中使用网格(即SauceLabs)时,我遇到了一些障碍。当我的测试完成后,最好发回更新以指示测试是失败还是成功。要利用它,我需要 RemoteWebDriver 实例中的 sessionId。这可以在自定义Reporter 中获得,但是我无法确定此接口是否成功。由于我正在扩展 GebReportingSpec,因此我尝试创建自己的自定义版本,该版本具有自定义 Junit 规则来跟踪成功或失败:

public class TestSuccess extends TestWatcher {
  boolean success;
  String message;

  @Override
  protected void starting(Description d) {
    message = d.getMethodName();
  }

  @Override
  protected void succeeded(final Description description) {
    System.out.println("Test Success [succeeded] " + description);
    this.success = true;
  }

  @Override
  protected void failed(final Throwable e, final Description description) {
    System.out.println("Test Success [failed] " + description);
    this.success = false;
  }

  public boolean isSuccess() {
    return success;
  }

  @Override
  public String toString() {
    return message + " success: <" + success + ">.";
  }
}

然后我将它添加到我的 CustomReportingSpec:

class CustomReportingSpec extends GebReportingSpec {
  /* I also tried creating this as a RuleChain with:
   * @Rule TestRule chain = RuleChain.outerRule(
             super._gebReportingSpecTestName).around(new TestSuccess());
   * however, this results in a NPE.  Placing the super rule in the around 
   * still results in a NPE.
   */
  @Rule public TestSuccess _gebTestSuccesswatcher = new TestSuccess();

  // I never see this called
  void report() {
    System.out.println("Custom Reporting Spec: " + _gebTestSuccesswatcher + "\t")
    super.report()
  }
}

我还尝试在自定义报告器中进行设置:

public CustomReporter extends ScreenshotAndPageSourceReporter implements Reporter {
  @Rule
  public TestSuccess _gebTestSuccesswatcher = new TestSuccess();

  @Override
  public void writeReport(Browser browser, String label, File outputDir) {
    System.out.println("Custom Reporter: " + _gebTestSuccesswatcher);
    super.writeReport(browser, label, outputDir)
  }
}

但是,无论我的测试是否失败,似乎都会调用观察者上的成功方法。这是我的示例测试:

class OneOff extends CustomReportingSpec {
  def "Check One off"() {
    when:
      go "http://www.google.com"
    then:
      1 == 2
  }
}

还有输出:

Custom Reporter: null success: <false>.
Test Success [succeeded] Check One off(OneOff)

如您所见,成功方法在此失败测试完成后被调用。如果我修改测试以通过(即 1 == 1),这是我的输出:

Custom Reporter: null success: <false>.
Test Success [succeeded] Check One off(OneOff)

我有什么方法可以让这条规则在自定义报告器中正常工作?或者有没有办法在扩展中获取浏览器实例?我已经按照this guide 创建了自定义注释和侦听器,但我无法访问 Browser 对象。我试图在浏览器的声明中添加一个@Shared,但它并没有在 Geb 配置中拉取那个。

【问题讨论】:

  • 如果您只需要会话 ID,您就不能使用 browser.driver.sessionId(从规范中)获得它吗?
  • 虽然如此,但我想避免在每个功能测试结束时调用一个方法来更新测试,并且在失败时自动更新会很好——那就是我真正关心的功能。
  • 你可以编写一个基类,或者一个注册拦截器的Spock扩展,或者一个org.junit.rules.MethodRule。他们每个人都可以访问规范实例,因此也可以访问会话 ID。
  • 有趣的是 MethodRule 适用于扩展规范。如果您将其添加为答案,我将接受。我有兴趣了解为什么上面的第二个 TestWatcher(即 TestSuccess)不起作用。

标签: groovy junit webdriver spock geb


【解决方案1】:

由于 Spock 的 TestRule 支持存在已知限制,您的 TestSuccess 类无法正常工作。由于 Spock 和 JUnit 的测试执行模型之间存在细微差别,即使测试失败,从 TestRule 调用 base.evaluate() 也不会在 Spock 中引发异常。在许多情况下,这不会产生影响,但对于 TestWatcher 会产生影响。

这是 Spock 规则支持中唯一已知的限制,希望我们能在某个时候找到克服它的方法。使用MethodRule 时没有这种语义不匹配。

如果您想在 JUnit 规则的帮助下实现您的要求(我认为这很好),MethodRule 可能是更好的选择。与TestRule 不同,MethodRule 提供对测试实例的访问,这将允许您使用browser.driver.sessionId 获取会话 ID。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2016-06-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-01-27
    • 1970-01-01
    相关资源
    最近更新 更多