软件测试是失败者的赌注

本文是翻译,版权归原作者所有


原文地址(original source):http://spage.fi/software-testing

在看本文时,切记测试不是为了提高质量。提高质量的唯一方式是修改产品,测试不会改变产品。

测试的目标是收集产品信息,当然,这种信息在改善产品时可以被用到。

对于软件测试,我的意思是在产品开发阶段之间和之后的某些情况下,我们测试工程师所做的检查。管理员可以创建新用户吗?自动同步可以从连接问题中恢复吗?这个输入框接受多字节的 UTF-8 字符?等等类似的问题。

或许软件测试最重要的不是单元测试、可用性测试、性能测试、验收测试或任何其它非功能性的测试。

检查与 90 年代的相关性

关于测试工程师在开发阶段做了大量检查而没有在其它地方做太多的当前模式,是来自于早期的人为现象,在互联网之前的日子赢了每一场战斗。

在一切都是网页以及我们所有设备都能不间断地访问互联网之前,收集产品信息的唯一方式就是测试。没有可查的服务器日志、崩溃报告和 UI 标准。

在过去,如果你一周能够得到一个版本就是幸运的。第一个可行的单元测试框架诞生于 1998 年(SUnit,xUnit家族第一成员【注1】),因此,“如果它编译了,那么它就没问题”成了标准。

收集关于产品任何信息的唯一方式是做大量测试。

回到现在

今天状况完全不同了。

很快我们所有设备都可以始终访问互联网了。如果我们避开操作系统和 web 浏览器,那么我猜想,我们消费的大部分软件实际上正运行在软件所有者的机器上。我这里讨论的是网页。

因此大部分软件正运行在这样的机器上,以致于开发者能够得到真正详实的使用数据、错误报告以及所有细致的日志信息。所有这些信息在20年前都是获取不到的。

当然,我们用来得到这些日志和报告的同样渠道,也可用于发布、更新软件。

20 年前,当你发布一款软件产品时,你将其刻在 CD 上,放入纸板盒,逐个将产品发往某个地方。你不知道谁在真正地使用产品,因为它是被实体店买走的,你没有去卖它。一些零售商在处理这些事务。

因此你根本不知道软件在客户机器上是否真正运行。即使你知道某些功能不好用或在某些条件下不能运行,你也没有办法更新软件。因为你不知道谁在用你的产品。

当周围环境发生变化时,我们需要重新思考该如何使用我们的资源。过去唯一理智的做法就是尽可能保证没有 bug,因为如果有任何种类的问题,修复它们几乎是不可能的,你的软件也无法报告给你。

现在推论就有了,在发布前尽最大人力做大量测试的行为,还算是最聪明的策略吗?据我看,不是。

在我看来,我们应当把精力放在尽可能确保原始代码的质量上,产品版本是我们实际想要的东西,我们也在真正地关注着版本。我们应该尽可能多地监控产品使用情况。为了对产品反馈给我们的数据做出反应,我们必须确保产品易于修改和维护。

接下来呢?

我们应该帮助开发者写出更好的代码,而不是整天放在检查工作上。我们应该提倡更好的开发实践,我们应该教他们使用持续集成系统,更好的版本控制系统,单元测试、代码审查、静态分析和其它最佳实践。

我们应该通过建立纸面原型(paper prototype)以及做一些走廊可用性测试【注2】来帮助产品所有者。我们应该确保这个版本被真正实现了。

我们应该编写小程序,以自动地验证产品核心组件的功能。这里,我故意避免测试自动化,因为我想强调这种技能是必需的。

我们应该测试产品的初始版本尽可能没问题,这实际上是有要求的。产品接下来的开发应该尽可能容易。

为什么?

初始代码质量越好,产品后续工作就越容易。当有验证核心组件功能的自动化测试用例时,产品后续工作就更有保障了。当开发过程和版本控制都处于良好态势时,产品后续工作就更加容易。同样还有经过同行评审【注3】和单元测试的代码等。当我们确保代码质量处于这种状态时,修改和修复产品就更容易了,我们能够更加容易地对变化做出反应。较好的代码质量意味着 bug 更容易修复、新的开发人员能够在较短时间内接手产品等。

我们应该抛弃发布重度测试过的产品的懒惰思维,而要关注发布一个尽可能容易修改的产品。

通过帮助产品所有者验证他们的想法,我们可以更容易地找到失败之处。当我们确保这些想法真正被实现时,我们才真正地得到了符合要求的产品。

长话短说

这里用摘自 GTAC 2014 的一张不错的幻灯片做为总结:

GTAC 2014 测试哲学

译文:软件测试是失败者的赌注 》| 腊八粥