2009-02-17 28 views
8

如果一个项目有100%的单元测试覆盖率,是否仍然需要集成测试?如果一个项目有100%的单元测试覆盖率,是否仍然需要集成测试?

我从来没有在100%单元测试覆盖率的项目上工作过,但是我想知道您的项目是否获得这个(或90%),您的体验还是需要集成测试吗? (你需要更少?)

我问,因为集成测试看起来很糟糕。它们通常是缓慢的,脆弱的(容易突破),不透明的(当某人不得不通过所有图层来找出错误时),并且导致我们的项目放缓下来......我开始认为有只有单元测试(也许是一小撮烟雾测试)才是最好的选择。

从长远来看,集成测试(根据我的经验)似乎比他们节省的成本更高。

感谢您的考虑。

回答

16

定义

我认为在进行此讨论之前定义您的术语很重要。

单元测试单独测试一个单元。对我来说,这是一堂课。单元测试将创建一个对象,调用一个方法并检查结果。它回答了这个问题:“我的代码是否按照我的意图去做?”

集成测试测试系统中两个组件的组合。它侧重于组件之间的关系,而不是组件本身。它回答了“这些组件是否按预期一起工作”的问题。

系统测试测试整个软件系统。它回答了这个问题:“这个软件是否按照预期工作?”

验收测试是一个自动化的方式,让客户回答“我想这个软件是我想要的吗?”这个问题。这是一种系统测试。

请注意,这些测试都不能回答“这个软件有用吗?”这样的问题。或者“这个软件容易使用?”。

所有的自动化测试都受限于公理“端到端比你想象的要进一步”“ - 人类最终必须坐在电脑前,看看你的用户界面。

比较

单元测试是更快,更容易编写,运行更快,更容易诊断。它们不依赖于像文件系统或数据库这样的“外部”元素,因此它们更简单/更快/更可靠。大多数单元测试在重构时继续工作(并且良好的单元测试是安全重构的唯一方法)。他们绝对要求你的代码是decoupled,这很难,除非你先写测试。这些因素的结合使得TDD的红/绿/重构序列工作得很好。

系统测试很难写,因为他们必须经过这么多的设置才能达到想要测试的特定情况。它们很脆弱,因为之前软件行为的任何变化都会影响到您想要测试的情况,即使这种行为与测试无关。出于类似的原因,它们比单元测试慢得多。故障诊断可能非常困难,因为故障可能需要很长时间才能完成,而且故障涉及的软件太多。在某些软件中,系统测试非常难以自动化。集成测试处于两者之间:它们比系统测试更易于编写,运行和诊断,但覆盖范围比单元测试更广。

推荐

使用测试策略的组合来平衡每个的成本和值。

4

是的,除了有几个不同类型的代码覆盖率

from wiki:

  • 功能覆盖 - 已执行程序中的每个函数?
  • 语句覆盖范围 - 每行源代码是否都已执行?
  • 决策覆盖(也称为分支覆盖) - 每个控制结构(如if语句)都评估为真和假吗?
  • 条件覆盖率 - 每个布尔子表达式都被评估为true和false(这不一定意味着决策覆盖率)?
  • 修改条件/决策覆盖范围(MC/DC) - 决策中的每个条件是否至少对所有可能的结果采取一次?是否显示每个条件都独立影响决策结果?
  • 路径覆盖 - 是否已经执行了代码中给定部分的所有可能路径?
  • 进入/退出覆盖范围 - 是否已经执行了所有可能的调用和返回功能?

例如,仅仅因为每个方法都被调用,并不意味着如果您按给定顺序调用各种方法,则不会发生路径覆盖。

15

是的。

即使所有“单位”都做他们应该做的事情,但不能保证整个系统按设计工作。

1

单元测试与集成测试不同。只是为了说明一点:如果我必须选择,我会转储单元测试并进行集成测试。经验告诉我们,单元测试有助于确保功能,并在开发周期的早期发现错误。

集成测试是在产品看起来接近最终用户的情况下完成的。这一点也很重要。

+0

如果“经验告诉单元测试有助于确保功能并在开发周期的早期发现错误”。为什么你要“倾倒单元测试并进行集成测试”? – 2009-02-17 15:43:07

+0

“只是为了表达一点”。旧时间练习一直是为了完成测试工作。经验表明,如果您早期进行测试(并且迭代地),则有一些优势,例如尽早发现错误。现在,如果我倾销单元测试进行集成测试,那么我会失去这种优势,但我的项目仍然存在。 – Sesh 2009-02-17 15:59:54

1

单元测试通常都是关于单独测试你的课程。他们的设计应该确保您的班级具有可预测和预期的行为。

集成测试通常都是关于如何组合测试您的课程以及使用这些课程的“外部”程序。他们应该专注于确保当整个产品使用您的课程时,它以正确的方式进行。

0

是的,因为你的软件的功能取决于它如何与不同的部件进行交互。单元测试取决于您输入输入和定义预期输出。这样做并不能保证它可以与你系统的其他部分一起工作。

是的集成测试是一个痛苦的问题,当您引入代码更改故意更改输出。通过我们的软件,我们可以通过将集成测试的保存结果与保存的正确结果进行比较来最大限度地减少此问题。

我们有一个工具,可以使用,当我们确信我们正在产生正确的结果。它会加载旧保存的正确结果并修改它们以使用新的设置。

2

首先,即使在单元测试级别,100%的单元测试覆盖率也不够:只覆盖代码指令的100%。你的代码中的路径怎么样?输入或输出域如何?

其次,您不知道发送器单元的输出是否与来自其接收器单元的输入兼容。这是集成测试的目的。

最后,单元测试可能在与生产不同的环境下执行。集成测试可能会显示差异。

1

“不透明(当某人不得不穿透所有图层以找出错误时)” - 这正是集成测试完成的原因 - 否则这些不透明的问题将显示在生产环境中。

0

我经常看到好的集成测试发现的各种问题 - 特别是如果您可以自动化一些集成测试。

单元测试很好,但是您可以在单元测试中没有100%相关性的情况下完成100%的代码覆盖率。你真的想要测试不同的东西,对吧?在单元测试中,通常是针对特定功能寻找边缘案例,而集成测试将在所有这些功能交互时向更高层展示问题。

如果你在你的软件中建立一个API,你可以用它来进行自动集成测试 - 过去我已经获得了很多里程数。我不知道我会尽可能地说我倾向于单元测试而不是集成测试,但是当它们做得正确时,它们是一个非常强大的补充。

0

This exact question基本上刚刚问过一天前。请参阅this question了解可能会遇到的很多错误,即使使用100%的代码覆盖率也是如此。

2

您只能使用测试/覆盖来证明存在错误,但您永远无法使用测试/覆盖来证明该代码没有错误。这个事实表明了测试/覆盖的界限。这在数学上是一样的,你可以通过找到一个反例来驳倒一个定理,但是你永远不能通过找到一个反例来证明一个定理。因此,测试和覆盖仅仅是正确性证明的替代品,这些证据很难做到几乎从不使用。测试和覆盖可以提高代码的质量,但不能保证。它仍然是一门手艺而不是科学。

0

它看起来并不像这里提到的那样,但你实际上从来没有100%的单元测试覆盖率(如果你有一个数据库)。当您为数据库连接和CRUD操作编写单元测试时,您刚刚创建了一个集成测试。原因是因为您的测试现在在各个工作单元之外有依赖性。我所从事的项目以及与之交谈过的开发人员一直都表示剩余的10%是DAO或服务层。最好的测试方法是使用集成测试和模拟(内存)数据库。我已经看到为了单元测试DAO而尝试模拟连接,但我并没有真正看到这一点 - 您的DAO只是将原始数据从一种格式序列化到另一种格式的一种方式,而您的经理或代表将决定如何操纵它。

2

我还没有真正看到涵盖这些考虑的答案。现在,我从整体系统角度来讲,并不构成软件开发的角度,但... 集成基本上是将低级产品组合到更高级别产品中的过程。每个级别都有自己的一套要求。尽管某些要求可能相同,但对于不同的等级,总体要求会有所不同。这意味着不同级别的测试目标是不同的。另外,较高级别产品的环境环境往往与较低级别产品的环境环境不同(例如,SW模块测试可能发生在桌面环境中,而完整的可加载SW项目可能在加载到其HW中时被测试零件)。此外,较低级别的组件开发人员可能与高级产品开发人员对“需求和设计”的理解不一样,所以集成测试也在一定程度上验证了较低级别的产品开发。

相关问题