【问题标题】:JUnit: same tests for different implementations and fine grained result statesJUnit:针对不同实现和细粒度结果状态的相同测试
【发布时间】:2011-07-16 11:32:31
【问题描述】:

我们对同一个接口有两种不同的实现。将其视为参考和生产实现。这两个实现由不同的团队实现,目标是从两个实现中获得相同的结果。

创建参考实现的团队已经创建了大量基于 Junit 的测试用例(目前大约 700 个测试用例),并且这些单元测试在开发过程中经常运行。我们可以针对生产实现运行相同的测试用例集。

生产实施的功能通过回归测试进行测试。但是,能够针对生产实现运行单元测试可以让我们快速反馈每次我们获得生产代码的新版本时是否出现严重问题。

但由于生产版本中缺少某些功能,或者由于已知错误导致结果不同,因此并非所有测试都通过此实现。这使得早期发现回归变得困难。

这里有几个类别:

  • (A) 测试用例只对参考实现有意义,对生产实现永远不会重要

  • (B) 测试用例,在测试生产实现时只需要省略某些断言(即参考实现中报告的附加值)

  • (C) 已知由于某些功能的开发滞后而无法在生产实现中工作的测试用例,但应稍后包含

到目前为止,我们有以下选择:

  • 用 if 语句围绕仅在参考实现中有效的断言使我们的代码变得混乱。这解决了(B),但很难维护。

  • 使用假设真。这对于 (A) 来说是可以的,但给人的错误印象是 (B) 中的一切都好。

我想要的是

  • 能够基于运行时条件(例如使用假设真)跳过某些测试,但对于 (C),这些测试应报告为已跳过而不是成功

  • 有更多的结果状态,考虑到一个测试用例是否已知以前工作过,这给出了

    • 已知以前有效的测试用例成功
    • 已针对以前已知无法正常工作的测试用例进行了修复
    • 之前已知无法运行的测试用例失败
    • 已知以前有效的测试用例的回归
    • 已跳过

以前有没有人做过类似的事情,或者甚至可以使用 JUnit(最好结合使用 eclipse JUnit 插件)?

【问题讨论】:

    标签: java unit-testing junit automated-tests


    【解决方案1】:

    要跳过具有运行时条件的测试,您可以使用Filter,并且您可以根据测试的某个方面(名称,最好是注释@Development)选择忽略或不忽略测试,具体取决于运行时条件() 或 @Version() 在测试方法上)。

    要使用它来解决 (B),您需要为每个版本使用不同的测试方法,一种用于 3.1,一种用于 3.2,等等。这似乎会使您的单元测试变得混乱,但实际上它使您的工作更容易挑选出适用于 3.1 的测试。

    对于您问题的“时间机器”部分,junit 很难知道以前是否通过了测试。您需要在某处记录旧结果。

    要分析哪些测试的状态发生了变化(从通过变为失败),例如,让您的 junit 测试由 CI 系统以系统的方式运行,然后将结果保存在可以进行后处理以提供回归的地方.例如,surefire xml 报告相当容易解析。

    【讨论】:

      【解决方案2】:

      我不知道您问题的第一部分,但就多个结果状态而言,您可能需要某种持续集成。据我所知,JUnit 无法“知道”您的测试用例过去是成功还是失败,因此您需要在其他地方获取这些信息。

      【讨论】:

      • 我正在考虑以代码或注释的形式向 Junit 提供此信息。事实上,eclipse 插件确实支持从以前的运行中检索结果,但不支持比较,结果仅存储在本地机器上。 CI 部分已经在我今年晚些时候的清单上。
      • 说实话,我不知道 JUnit 提供任何支持来传递以前的测试结果。即使有办法做到这一点,它也可能必须涉及读取外部文件,因为每次测试结果发生时编辑代码/注释并不是很实用。您总是可以按照 MatthieuF 的建议检索结果并自己进行比较,但在我看来,这就像重新发明轮子。
      • 我提到的支持是由eclipse插件提供的,而不是JUnit本身。虽然必须手动注释测试用例需要更多的工作,但它的优点是能够标记应该工作的测试用例,即使在上一个版本中它失败了。考虑一下,在运行时通过@ExpectSuccess(condition="version>=123") 之类的条件设置此设置将是一个不错的功能。
      【解决方案3】:

      您能否创建一个包含所有已知在这两种情况下都有效的测试用例的基类,并使用另外两个包含特定于生产和参考实现的测试用例的类来扩展它?

      如果它比这更细化(例如,一个测试很长,并且 90% 的测试在 prod 和 reference 中都有效),那么您可以采用相同的方法,但将不同的断言放在子类中的覆盖方法中. (您必须在基类中创建许多抽象方法来支持这一点)

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2015-03-22
        • 1970-01-01
        • 1970-01-01
        • 2012-01-02
        相关资源
        最近更新 更多