gpt4 book ai didi

java - 我应该编写单元测试来检查@NonNull 契约(Contract)吗?

转载 作者:行者123 更新时间:2023-11-29 07:49:41 26 4
gpt4 key购买 nike

今天我和一些同事讨论了单元测试。一个有争议的方面是您是否需要对一个函数的所有契约进行单元测试。

例子:

public void foo(@NonNull Type1 arg1, @NonNull Type2 arg2) {
requireNonNull(arg1);
requireNonNull(arg2);

// ...
}

虽然我同意在实现(Objects.requireNonNull 语句)中检查 @NonNull 契约是个好主意,但我不同意你应该写对其进行单元测试。

这是一个例子:

 @Test(expected = NullpointerException.class)
public void fooMustThrowIfArg1IsNull() {
Type2 dummy = ...;
foo(null, dummy);
}

到目前为止,我试图更多地关注您编写的代码的行为。据我了解 TDD 和 BDD 风格,你总是从测试开始,然后实现足以通过测试,等等。但是,我从未见过 TDD 或 BDD 从业者从上述测试开始。

我同意你应该让你的单元测试尽可能简单以隔离不同的方面(尽可能少的断言)。但我担心像 fooMustThrowIfArg1IsNull 这样的测试的维护成本高于 yield ,即使您忽略了编写它所需的时间。我看到的唯一异常(exception)是对关键 API 的测试(例如,Java 标准库实现或 Google Guava)。

由于该主题自以为是,因此很难简单地回答是或否。通过指向专家选项的链接以及关于该主题的明确建议来支持它会很有帮助。可能的来源:

  • 具有深厚测试文化的公司(例如 Google)的风格指南
  • 公认的测试专家的引述或代码示例

(我发现搜索引擎并不是很有用,不幸的是我还没有读过任何关于测试的书。)

最佳答案

嗯,没有确定的答案。但是,检查代码的契约似乎是个好主意。如果没有样板代码...

我在 Google Guava's 中发现了一种有趣的方法来源。例如,此测试是 SplitterTest.java 的一部分:

@GwtIncompatible("NullPointerTester")
public void testNullPointers() {
NullPointerTester tester = new NullPointerTester();
tester.testAllPublicStaticMethods(Splitter.class);
tester.testAllPublicInstanceMethods(Splitter.on(','));
tester.testAllPublicInstanceMethods(Splitter.on(',').trimResults());
}

因此,至少 Google 开发人员测试了他们的空契约(Contract)。 (NullPointerTester 的 Grepping 结果为 335 次命中。)

NullPointerTester 假定未标记为 @Nullable 的构造函数和方法在传入 null 时应立即失败。他们将失败定义为抛出 NullPointerExceptionUnsupportedOperationException

我认为这是一个非常好的技巧。他们获得了测试快速失败语义的所有好处,但避免编写大量枯燥、机械的测试。

那么,是否应该编写单元测试来检查快速失败 @NonNull 契约?也许让反射为您完成这项工作会更好。 :-)

关于java - 我应该编写单元测试来检查@NonNull 契约(Contract)吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22262570/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com