【问题标题】:TDD and "honesty" of testTDD和测试的“诚实”
【发布时间】:2014-10-20 07:23:25
【问题描述】:

在进行 TDD 时,我担心测试的“诚实”。 TDD 是

  1. 写红色测试
  2. 编写足够的代码使其变为绿色
  3. 重构,让测试变绿

到目前为止一切顺利。现在这里是一个应用上述原理的例子,这种例子在教程和现实生活中已经遇到过:

我想检查当前用户的电子邮件是否显示在我的 webapp 的默认页面上。

  1. 编写红色测试:“example@user.com”显示在 default_page.html 中
  2. 编写足够的代码使其变为绿色:在 default_page.html 中硬编码“example@user.com”
  3. 通过实现 get_current_user()、其他层中的一些其他代码等进行重构,让测试变为绿色。

我对第 2 步感到“震惊”。这里出了点问题:即使没有实际工作,测试也是绿色的。这里有一种测试气味,这意味着也许在某些时候有人可以在不破坏测试套件的情况下破坏生产代码。

我在这里缺少什么?

【问题讨论】:

  • 是什么让您认为将文本硬编码到页面上符合“编写足够的代码使其变为绿色”的条件?当然,它确实具有测试测试有效的好处。
  • @T.J.Crowder 因为不幸的是,这是著名的 TDD 书籍所支持的那种废话。
  • @OliverCharlesworth:嗯,正如我所说,它有测试测试的好处,这是一件至关重要的事情......
  • 这是真的:这三个步骤并不包含所有的软件开发。它们只是路标。是的,您可以按照描述对它们进行游戏,就像您可以玩任何“三步过程”一样。不过,不要那样做,你会没事的。如果您真的担心其他人会担心,您可以让测试为每次运行随机生成一个不同的电子邮件地址。
  • @T.J.Crowder 我不同意“测试测试”。测试同时测试自身和被测对象。

标签: unit-testing testing tdd atdd


【解决方案1】:

您关于“没有任何工作”的断言是错误的。对于电子邮件地址为 example@user.com 的情况,该代码可以正常运行。而且您不需要最后的重构。您的下一个失败测试可能是在用户拥有不同电子邮件地址的情况下使其失败。

【讨论】:

  • +1 OP 正处于过程的中间,需要添加更多测试来确定他们想要的确切行为
【解决方案2】:

我会说你所拥有的只是部分完成。你说:

我想检查当前用户的电子邮件是否显示在我的 webapp 的默认页面上。

测试不会检查默认页面上的当前用户电子邮件地址,它会检查页面中是否存在固定的电子邮件地址“example@user.com”。

要解决这个问题,您要么需要提供更多示例(即有多个使用不同电子邮件地址的测试),要么在测试设置中随机生成电子邮件地址。

所以我会说你所拥有的是这样的伪代码:

Given current user has email address "example@user.com"
When they visit the default page
The page should contain the email address "example@user.com"

这是您可以在 TDD 中编写的第一个测试,您确实可以对其进行硬编码以避免实现不必要的内容。您现在可以添加另一个测试,这将强制您实施正确的行为

Given current user has email address "example2@user.com"
When they visit the default page
The page should contain the email address "example2@user.com"

现在您必须删除硬编码,因为您无法使用硬编码解决方案同时满足这两个测试。因此,这将迫使您从当前用户那里获取 实际 电子邮件地址并显示此地址。

在您的测试中以 3 个示例结束通常是有意义的。这些不需要是 3 个单独的测试,您可以使用数据驱动测试来重用具有不同值的相同测试方法。你没有说你用的是什么测试框架,所以我不能举一个具体的例子。

这种方法在 TDD 中很常见,称为 triangualtion。

【讨论】:

  • 是的,但是...很多书籍,包括著名的amazon.com/Test-Driven-Development-Kent-Beck/dp/0321146530/… 都建议不要过度使用三角测量。使用三角剖分重构测试通常会更好(并使测试更加连贯)。此外,随机生成用户名在单元测试中并不是一个很好的做法(任何带有“随机”一词的东西都不应该真正出现在单元测试中)。不过,很好的答案 +1
  • 关于三角测量的要点。我不确定我是否同意测试中的“没有随机”。有时您只需要一个值而不需要它是特定的东西,并且“随机”生成数据可以避免将解决方案编码为测试数据。如果您对随机对象使用相同的种子,那么您每次都保证相同的测试数据,尽管它是随机生成的。这消除了由于测试数据而导致测试随机失败的担忧。 AutoFixture 是为提供此类数据而编写的框架。
【解决方案3】:

你说得对

第2步.这里有问题

但它不在TDD 方法中。恕我直言,它在测试逻辑中。毕竟这(第 2 步)验证了测试工具是否正常工作。新的测试不会错误地通过而不需要任何新代码,并且所需的功能还不存在。

我在这里缺少什么?

这一步还应该测试测试本身,是否定的:它排除了新测试总是通过的可能性,因此没有价值。由于预期的原因,新测试也应该失败。至关重要的是,此步骤可以增强开发人员对其测试正确事物的信心,并且仅在预期的情况下通过。

【讨论】:

    猜你喜欢
    • 2021-04-11
    • 2010-10-07
    • 1970-01-01
    • 2017-08-26
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-03-14
    • 2023-03-05
    相关资源
    最近更新 更多