【问题标题】:What is the best practice when unit testing methods that have assertions instead of exceptions?当单元测试具有断言而不是异常的方法时,最佳实践是什么?
【发布时间】:2015-04-07 10:43:58
【问题描述】:

假设你有一个这样的公共方法

public Sprite spriteAt(int x, int y) 
{
    assert withinBorders(x, y) : "PRE: x and y should be inside the borders";

    return tileAt(x, y).topSprite();
}

对比

public Sprite spriteAt(int x, int y)
{
    if (!withinBorders(x, y)) throw new InvalidArgumentException();

    return tileAt(x, y).topSprite();
}

在最底层的情况下,我通常会有一个单元测试用例来检查当给定 x 和/或 y 的无效值时是否引发异常,如下所示:

@Test(expected = InvalidArgumentException.class)
public void SpriteAt_InvalidX_ThrowsInvalidArgumentException()
{
    sut.spriteAt(-100, 0);
}

这个测试用例是为了确保方法中实现了参数验证逻辑。

但是,对于顶部的断言方法,我不确定我应该做什么。断言不是生产代码,我认为这意味着我不必测试断言。

另一方面,我认为当方法中的逻辑发生变化时,单元测试应该通过失败来通知开发人员。如果我不编写测试用例来检查是否存在检查无效参数的断言(就像我对异常方法所做的那样),那么当我不小心删除了断言行代码时,我可能没有意识到我犯了一个错误。

因此,如果在启用断言的情况下运行 junit 并且在未启用断言时不做任何事情,我想做的是检查断言是否到位。下面的代码将包含伪代码。

@Test
public void SpriteAt_InvalidX_AssertionThrowsException()
{
    if (assertion is enabled)
    {
        try
        {
             sut.spriteAt(-100, 0);
             fail();    
        }
        catch (AssertionFailureException e)
        {
        }
    }
}

回到我的观点。我想知道单元测试是否应该测试断言。如果是这样,我是否朝着正确的方向前进?如果没有,如何防止在没有单元测试的情况下意外删除断言代码?

【问题讨论】:

    标签: java unit-testing exception junit assertions


    【解决方案1】:

    有趣的问题。

    在我看来,如果您想要测试xy不在明确范围内的情况,那么您应该抛出IllegalArgumentException而不使用assert。另一方面,您没有方法注释告诉此方法的调用者xy必须在一个范围内。因此,如果您从调用者的角度来看,您根本没有权利断言这一点。 :-p

    我会使用assert 来检查我没有单元测试的前提条件。但另一方面,您应该对该示例进行单元测试。

    在一天结束时assert 也会抛出一个RuntimeException,并且-正如您所说-仅在开发期间编译器标志是这样的。那么为什么不简单地使用看起来非常适合这种情况的IllegalArgumentException。并且请给方法的调用者提示,在这种情况下,它会与@throws 注释一起抛出。

    我的结论是:assert 只要你有良好的单元测试覆盖率就没什么用了。 仅适用于开发期间的手动测试,以检查您不希望或可以为其编写显式单元测试的前提条件。

    【讨论】:

      【解决方案2】:

      如果您使用-ea java 命令参数将其打开,您始终可以测试assert 功能。

      assert 抛出 java.lang.AssertionError

      单元测试应该测试行为,而不是实现。因此,如果合约 (JavaDoc) 中未明确定义断言行为,则不应对其进行测试。

      assert 非常无用,几乎从未在实际系统中使用过。

      【讨论】:

      • 你能详细说明你的最后陈述吗?我也觉得断言不是太重要(除了单元测试),但我还是个大三学生。
      猜你喜欢
      • 2023-03-10
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-07-16
      相关资源
      最近更新 更多