我多年的软件开发经验表明,实际上它是行不通的。
你试过了吗?我和Dave都是根据我们自己以及ThoughtWorks的其他资深人士多年的集体经验写的书,实际上是在做我们讨论的事情。书中没有任何东西是推测性的。我们讨论的所有内容甚至在大型分布式项目中都经过了尝试和测试。但是我们不建议您出于信仰。当然,您应该自己尝试一下,并写下您发现有用的内容和不起作用的内容(包括相关的上下文),以便其他人可以从您的经验中学习。
持续交付非常注重自动化测试。我们花了大约1/3的书来谈论它。我们这样做是因为替代方法-手动测试-昂贵且容易出错,而且实际上并不是构建高质量软件的好方法(如Deming所说:“停止对大规模检查的依赖以实现质量。改进过程并将质量纳入首先的产品”)
无法全面覆盖测试。对于每件事,您都必须投入大量时间-时间就是金钱。这是有价值的,但是可以花费时间以其他方式为质量做出贡献。
当然,完全的测试范围是不可能的,但是还有什么选择:零测试范围?需要权衡。介于两者之间的位置是您项目的正确答案。我们发现,一般来说,您应该花费大约50%的时间来创建或维护自动化测试。在您考虑进行全面的手动测试以及修复向用户发布的错误的成本之前,这听起来可能很昂贵。
有些事情很难自动测试。例如GUI。甚至Selenium也不会告诉您您的GUI是否不稳定。
当然。查看Brian Marick的测试象限。您仍然需要手动执行探索性测试和可用性测试。但这就是您应该将昂贵且有价值的人用于-而不是回归测试。关键是您需要放置一个部署管道,这样您才可以对已经通过了全面的自动化测试套件的内部版本进行昂贵的手动验证。因此,你既减少的钱,你对手动测试花费的金额,并不断使其手动测试或生产缺陷的数量(到那时他们是很要修复昂贵)。在产品的整个生命周期中,正确完成自动测试的成本要低得多,但是随着时间的推移,这笔资本支出会摊销自己。
没有笨拙的固定装置,很难测试数据库访问,甚至无法覆盖数据存储中的奇怪情况。同样的安全性和许多其他事情。只有业务层代码才可以有效地进行单元测试。
通过基于端到端方案的功能接受测试对数据库访问进行隐式测试。安全将需要自动和手动测试的结合-自动渗透测试和静态分析,以发现(例如)缓冲区溢出。
即使在业务层中,大多数代码也不是简单函数,其参数和返回值可以很容易地隔离以进行测试。您可能会花费大量时间来构建模拟对象,这可能与实际实现不符。
当然,如果您构建软件且测试很差,则自动化测试会很昂贵。我强烈建议您阅读“在测试的指导下不断发展的面向对象软件”这本书,以了解正确的做法,以便随着时间的推移可以维护您的测试和代码。
集成/功能测试是对单元测试的补充,但是它们需要大量时间才能运行,因为它们通常涉及在每个测试中重新初始化整个系统。(如果不重新初始化,则测试环境会不一致。)
我曾经使用的一种产品具有一套3500个端到端验收测试套件,需要运行18小时。我们在70个盒子的网格上并行运行它,并在45m内获得反馈。确实还比理想的还要长,这就是为什么我们在几分钟内运行完单元测试后,将其作为管道的第二阶段运行,因此我们不会在没有基本水平的构建上浪费我们的资源。信心。
重构或任何其他更改都会破坏很多测试。您花费大量时间修复它们。如果只需要验证有意义的规范更改,那很好,但是测试常常由于无意义的低级实现细节而失败,而不是真正提供重要信息的东西。通常,调整主要集中在重新测试内部,而不是真正地检查正在测试的功能。
如果您的代码和测试被很好地封装并且松散耦合,则重构不会破坏很多测试。我们在书中还描述了如何对功能测试执行相同的操作。如果您的验收测试失败,则表明您缺少一个或多个单元测试,因此CD的一部分涉及不断提高您的测试覆盖率,以尝试在交付过程中尽早发现错误,使测试的粒度更细,错误更便宜。
错误的现场报告无法轻松地与代码的精确微版本相匹配。
如果你的测试和更频繁的释放(CD点的一部分),那么它是相对简单的,以确定导致错误的改变。CD的全部目的是优化反馈周期,以便您可以在检入版本控制后尽快发现错误-实际上,最好在检入之前(这就是我们运行构建和单元测试的原因)签到之前)。