偶尔我来翻过一个单元的测试,并不断言任何东西。特定例子中我遇到了这个早晨是测试一登录文件得到了书面要当一个条件得到满足。假设是,如果没有错误被抛测试通过。

我个人没有一个问题,但它似乎被一个比一个"代码闻",以编写一个单元的测试,没有任何说法与它相关联。

只是想知道是什么人的看法,这是什么?

有帮助吗?

解决方案

这是正式的做法:

// Act
Exception ex = Record.Exception(() => someCode());

// Assert
Assert.Null(ex);

其他提示

这只是一个非常小的测试,应该记录在案。它仅验证它在运行时不会爆炸。关于这样的测试最糟糕的部分是它们呈现出一种虚假的安全感。你的代码覆盖率会上升,但这是虚幻的。非常难闻的气味。

如果没有断言,则不是测试。

退出懒惰 - 可能需要一点时间来弄清楚如何在那里得到断言,但值得知道它做了你期望它做的事。

这些被称为冒烟测试并且很常见。他们是基本的健全检查。但它们不应该是你拥有的唯一一种测试。你还需要在另一个测试中进行某种验证。

这样的测试闻起来。它应检查文件是否已写入,至少修改后的时间可能已更新。

我已经看过很多以这种方式编写的测试,最终没有测试任何东西,即代码不起作用,但它也没有爆炸。

如果您有一些明确的要求,即测试中的代码不会抛出异常并且您想明确地调出这个事实(测试为需求文档),那么我会做这样的事情:

try
{
  unitUnderTest.DoWork()
}
catch
{
  Assert.Fail("code should never throw exceptions but failed with ...")
}

......但这对我来说仍然有点味道,可能是因为它试图证明是消极的。

在某种意义上,您正在进行隐式断言 - 代码不会抛出异常。当然,实际获取文件并找到合适的行会更有价值,但我认为有些东西比什么都好。

在一般情况下,我看到这发生在一体化试验,只是一个事实,即东西成功地完成是不够好。在这种情况下Im酷。

我想如果我看见它并且再次在 单元测试 我会好奇的是如何有用的测试真的是。

编辑:在给出的实例中,通过运,有一些测试的结果(结果文件),所以假设,如果没有差错扔了它的工作是懒惰。

这可能是一个很好的实用解决方案,特别是如果替代方案根本没有测试。

问题是如果调用的所有函数都是no-ops,测试就会通过。但有时候验证副作用是否符合预期是不可行的。在理想的世界中,有足够的时间为每次测试编写支票......但我不住在那里。

我使用此模式的另一个地方是在单元测试中嵌入一些性能测试,因为这是让它们在每次构建时运行的简单方法。测试没有断言任何东西,但是测量测试花了多长时间并记录下来。

之前我见过这样的事情,我认为这只是为了支持代码覆盖率。它可能不是真正测试代码行为。无论如何,我同意将其(意图)记录在测试中以保持清晰。

测试的名称应该记录下来。

void TestLogDoesNotThrowException(void) {
    log("blah blah");
}

测试如何验证是否在没有断言的情况下写入日志?

我必须承认,我从未编写过单元测试,证明我正确记录。但我确实考虑过这个问题并遇到了这个讨论如何使用JUnit和Log4J完成。它不太漂亮,但它看起来会起作用。

测试应该始终断言,否则你会证明什么,以及如何能够始终如一地复制代码有效的证据?

我们一直这样做。我们使用JMock模拟我们的依赖项,所以我想在某种意义上JMock框架正在为我们做断言......但它就是这样的。我们有一个想要测试的控制器:

Class Controller {
  private Validator validator;

  public void control(){
    validator.validate;
  }

  public setValidator(Validator validator){ this.validator = validator; }
}

现在,当我们测试Controller时,我们不想测试Validator,因为它有自己的测试。所以我们对JMock进行了测试,以确保我们调用validate:

public void testControlShouldCallValidate(){
  mockValidator.expects(once()).method("validate");
  controller.control;
}

就是这样,没有“断言”。看,但当你打电话给控制和“验证”时如果没有调用该方法,则JMock框架会抛出异常(类似于“未调用的预期方法”等)。

我们到处都有。这有点落后,因为你基本上设置你的断言,然后调用测试方法。

我有时会使用我选择的单元测试框架(NUnit)来构建充当代码特定部分入口点的方法。这些方法对于分析代码子集的性能,内存消耗和资源消耗非常有用。

这些方法绝对不是单元测试(即使它们标有 [Test] 属性),并且总是被标记为在被检入源代码管理时被忽略并明确记录。

我偶尔也会将这些方法用作Visual Studio调试器的入口点。我使用Resharper直接进入测试,然后进入我想要调试的代码。这些方法或者没有使它成为源代码控制,或者它们获得了它们自己的断言。

我的“真实”单元测试是在正常的TDD周期中构建的,它们总是断言,但并不总是直接断言 - 有时断言是模拟框架的一部分,有时我能够将类似的断言重构为单个方法。这些重构方法的名称始终以前缀“Assert”开头。让我明白。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top