【问题标题】:Testing scenarios with exponentially growing outcomes结果呈指数增长的测试场景
【发布时间】:2013-08-08 16:02:46
【问题描述】:

真正吸引我关注 TDD 的一件事是在实现的同时清晰地开发规范。

我正在寻求实现一个接受配置对象的构造函数

function MyConstructor(conf) {}

conf 目前指定有两个键:a 和 b,其中 a 是 RegExp 和 b 是 Function,并且作为我的 TDD 规范的一部分阐明野心,我正在编写测试来指定这个对象:

  • 如果a 不是RegExp 或b 不是Function,我希望MyConstructor 抛出Error。
  • 如果配置中缺少a 或b,MyConstructor 将抛出Error。

现在,我知道我可以将此行为封装在其他构造函数中,比如创建“配置”对象的Configuration 构造函数。但是我现在看到的方式,无论这种行为在哪里结束,这种行为都必须封装在某处,以便通过 TDD 详细说明这个规范。

问题是:在我看来,随着conf 对象上的键数量的增加,测试的数量也在增加——呈指数增长!这尤其是由于上面的第二个项目符号。

例如,假设我有 4 个键:a、b、c 和 d,我需要确保如果缺少任何键,则会引发错误。 似乎这需要我编写大量相同的、平庸的测试来涵盖丢失键的所有可能性(组合!)。这听起来不对!然而,我想不出一种明确或归纳测试涵盖所有场景的好方法。有什么想法吗?

【问题讨论】:

  • 我对这个问题有点困惑。规范会指出,如果 ctor 缺少任意数量的任意数量的键中的任何一个,它将失败。您不必测试所有组合(无论如何您都可以通过编程方式进行),您只需确保是否缺少任何必需的键就会抛出。听起来像是简单的对象验证,其中存在预先构建的解决方案。
  • @DaveNewton,所以在我有限的单元测试经验中,我从未见过用循环或嵌套循环编写,迭代组合。您是说鉴于测试必须(a)快速(b)简单,这是一件好事吗? (不确定最后一个,但这是我的印象)。
  • 以有意义的方式以编程方式创建排列比手动编写相同的测试要慢吗?如果您实际上需要测试所有排列,它们也更有可能随着时间的推移变得更正确......如果我们只是谈论需要确保所有必需的参数都存在。
  • @DaveNewton,你是完全正确的,但我应该首先编写这些循环吗?我会 完全喜欢通过测试来说明我的规范的每一个细节,但我也不想对 JavaScript 做不应该对 JavaScript 做的思考。你怎么看?
  • 我没有看到以编程方式生成测试数据的问题。我什至以编程方式生成测试和规范,虽然不是在 JavaScript 中。

标签: javascript unit-testing testing


【解决方案1】:

没有类定义或接口的对象很难测试。如果你的对象是ducks,你需要使用ducktyping来检查。

您还可能想知道完全测试某些功能有多大用处。您可以测试边界,但永远无法测试所有值;

如果你的函数看起来像这样:

function sum(a, b) {
    if (a === 42) {
        throw new Error("All glory to the hypnotoad");
    }
    return a + b;
}

您希望如何找到这个错误?

【讨论】:

  • 所以,我在想,但没有在问题中提及。那是您的观点,那么,我应该如何详细说明规范? JS 不适合通过 TDD 进行规范?使用该语言最简洁的方法是简单地打字,而不是强调该语言不存在的功能。
  • JS 缺少接口,所以 TDD 受限。
  • 冷静下来,摩根。您始终可以引入自己的打字系统,但会产生一些开销。
  • 哈哈哈我在努力,我在努力。只是有点沮丧。是的,duck typing 很棒,但是我必须非常依赖于运行时行为的集成测试,对吧?
  • 嗯,模拟也不会那么容易,因为没有要模拟的规范。
【解决方案2】:

我建议您使用Duck Typing 来强制执行这些类型。从本质上讲,您要做的就是按照您的期望使用键传入的对象,并让 JS 运行时抱怨,例如,a 的行为不像 RegEx 或者您不能调用b 像一个函数。

【讨论】:

  • 天哪,太糟糕了。是的,我认为是这样,现在你们正在确认这种恐惧。通过 TDD 进行规范说明了这么多。我想我应该冷静下来!
  • 简而言之,测试黄金路径,并合理地记录好文档。相信您的对象的用户会做正确的事,并帮助他们知道那是什么。
  • DO 仍然通过 TDD 规范,只是不要指望它能解决人们错误地使用您的对象的问题! TDD 非常适合设计和指定对象的工作方式。它可以教你很多关于你的代码的知识。请记住,可以信任您的用户。
  • 谢谢@totallymike。我会这样做的。
  • 我将在我的右前臂上纹上“测试黄金之路”。
猜你喜欢
  • 2018-07-07
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-01-10
  • 1970-01-01
相关资源
最近更新 更多