42

Java(以及其他社区,我敢肯定)有一个众所周知的争论是否应该测试琐碎的 getter/setter 方法。通常,这是关于代码覆盖率的。让我们同意这是一场公开辩论,而不是试图在这里回答。

有几篇关于使用 Java 反射来自动测试这些方法的博客文章。

是否有任何框架(例如 jUnit)提供这样的功能?例如,一个注释说“这个测试 T 应该自动测试 C 类上的所有 getter/setter,因为我断言它们是标准的”。

在我看来,它会增加价值,如果它是可配置的,那么“辩论”将作为一个选项留给用户。

4

10 回答 10

17

我创建了OpenPojo项目来解决这个确切的问题。

该项目允许您验证:

  • 强制执行 Pojo 编码标准(即所有字段都是私有的,或者没有本地变量,...等)
  • 强制执行 Pojo 行为(即 setter 只进行设置,不进行转换等)
  • 验证 Pojo 身份(即使用基于注释的相等性和哈希码生成)

见教程

于 2011-02-25T19:36:13.157 回答
14

我不知道有任何现成的库或类可以做到这一点。这可能主要是因为我不在乎,因为我强烈反对这样的测试。所以即使你问这个观点一定有一些理由:

我怀疑自动测试 getter 和 setter 是否有益于您的代码质量或覆盖率:这些方法要么是从其他代码中使用的(并在那里进行了测试,例如 100% 覆盖),要么根本不使用(并且可以被删除)。最后,您将保留 getter 和 setter,因为它们是在测试中使用的,但在应用程序中没有其他地方使用。

编写这样的测试应该很容易,例如使用 Apache Commons BeanUtils,但我怀疑如果您有良好的测试,您是否真的需要它。

于 2008-09-20T16:50:30.547 回答
9

Unitils使用静态方法执行此操作assertRefEquals

于 2008-09-21T00:19:48.457 回答
7

在大多数情况下,setter 和 getter 只是设置和获取内部字段。一个对象必须检查它只包含有效值的内部规则。例如

  • 空值可能吗?
  • 空字符串可能吗?
  • 还是负值?
  • 还是零值?
  • 还是列表中的值有效?
  • 还是有最大值?
  • 或者 BigDecimal 值是否有最大精度?

如果存在无效值,则单元测试应检查行为是否正确。这不能自动化。

如果你对 setter 和 getter 没有逻辑,那么它必须在你的应用程序的任何地方使用。编写一个测试,其中您的对象是更复杂测试的参数。然后,您可以使用列表中的不同值对其进行测试。

测试您的业务逻辑,而不是 getter 和 setter。结果还应该涵盖 getter 和 setter。如果您只有一个公共库,这些方法也应该是您的业务逻辑中的任何结果。如果 getter 和 setter 没有代码覆盖,则将其删除。

于 2008-09-20T18:47:42.637 回答
5

我做过类似的事情。一个简单的 java 类,它接受一个对象并测试所有的 getter 和 setter 方法。 http://sourceforge.net/projects/getterandsetter/

我确实认为您应该尽可能避免使用 getter 和 setter 方法,但只要它们存在并且需要两行代码来测试它们,这样做是一件好事。

于 2008-10-25T21:02:13.710 回答
3

我会支持 OO 设计而不是代码覆盖率,看看我是否不能将这些字段移到需要它们的类中。所以我会尝试看看是否可以像之前建议的那样删除这些 getter 和 setter。getter 和 setter 正在打破封装

于 2008-09-20T17:07:45.937 回答
2

我正在尝试 openpojo

我踢了轮胎,它似乎完成了这项工作。

  1. 它允许您检查项目中的所有 pojo。
  2. 它似乎检查了 pojo 的最佳实践

查看本教程以获得快速入门 教程

于 2011-02-04T19:13:47.290 回答
1

我想这个图书馆是你问题的答案

它测试所有 bean 的初始值,the setters, the getters, hashCode(), equals() and toString()。您所要做的就是定义默认和非默认属性/值的映射。

它还可以测试带有其他非默认构造函数的 bean 对象。

于 2011-03-04T21:02:20.227 回答
0

由于我的声誉,在这里回答@me之前的评论:

Vlookward,不写 getter/setter 完全没有意义。设置私有字段的唯一选项是显式设置器,在构造函数中设置它们,或通过其他方法间接设置(功能上将设置器推迟到另一个地方)。为什么不使用二传手?

好吧,有时候,没有必要把这个领域保密(对不起,如果我的英语不是很好)。通常,我们编写软件是因为它是一个库,并且我们用不必要的 getter/setter 封装我们的字段(我们的业务逻辑字段)。

其他时候,这些方法实际上是必要的。那么,有两种可能:
1. 里面有业务逻辑。然后他们会接受测试,但他们不是真正的获取者/设置者。我总是在其他课程中编写该逻辑。并且测试测试其他类,而不是POJO
2.没有。然后,如果可以的话,不要手写。例如,下一个接口的实现可能是完全自动生成的(并且也在运行时!):

interface NamedAndObservable {
  String getName();
  void setName(String name);
  void addPropertyChangeListener(PropertyChangeListener listener);
  void addPropertyChangeListener(String propertyName,
                                 PropertyChangeListener listener);
}

所以只测试手写的内容。不管它是getter/setter。

于 2008-09-22T10:23:21.180 回答
0

我不会为每个属性编写测试用例,而是使用反射/内省来测试单个测试用例中的所有设置器/获取器以确定类型。这是一个很好的资源,显示了这一点:

http://www.nearinfinity.com/blogs/scott_leberknight/do_you_unit_test_getters.html

于 2011-07-20T14:07:32.087 回答