我先重申一些普遍的概念区别,以作为起点。
如果你听到别人在谈论敏捷项目中的测试,问一下那些测试是面向业务的还是面向技术的,会对你有很大的帮助。面向业务的测试是你可以用一个业务专家感兴趣的术语来向他描述测试。如果你通过电话描述测试回答了什么问题,你可以使用业务领域的术语:“如果你支取超过你的账户余额的现金,系统是否会自动给予你一笔与超出部分等额的贷款?”
面向技术的测试是你使用程序员的领域的术语来描述测试:“不同的浏览器会通过不同的方式实现Javascript,所以我们测试产品是否能在最主要的浏览器上工作。”或者:“如果用户记录不存在,PersistentUser#delete不应该执行。”
(这些分类有着很多模糊的界线,例如,选择测试哪个浏览器配置,部分是业务决定。)
问一下正在讨论测试的人,他们希望测试支援编程还是批判产品。对于“支援编程”,我的意思是程序员把测试作为编程的主要组成部分。例如,一些程序员编写测试用例来告诉他们下一步应该写什么代码。通过编写那些代码,他们改变一些程序的行为。这些更改之后通过运行这部分的测试来保证他们修改的是他们需要的。运行其它的测试来确保更改的行为不会影响其它不需要更改的部分。
批判产品的测试则不是专注于编程方面。而是在已完成的产品上查找发现产品的不足之处。
如果把这两类区别放到一起,就得到下面的矩阵图:
接下来,我会谈谈这个矩阵的每个区域,我关于它们的发展的预测。
左边是偏向“支援编程”的测试,右边是偏向“批判产品”的测试。但是两种测试的意义和内涵存在很大的不同。
对于支援编程,测试主要作为准备和保证。你通过写测试代码来阐明关于问题的思考。你把它作为说明性的例子来描述代码应该怎样做。幸运地是,它同时是活跃地检查代码的说明性例子,即重新保证。这些测试也会找bug,但是那是第二目的。
在另一方面,测试是关于暴露主要错误和遗漏。这里,测试的原义就是关于bug。有其它的意义,但是首要的意义是最主要的。(很多测试员,尤其是最好的测试员,在他们的身上已经融入了那些词语的内涵。)
我想做个尝试。如果我们在矩阵的左边不使用“testing”和“test”这些词语会怎样?如果我们把它叫做“checked examples”(检查例子)怎样?
设想两个XP程序员坐在代码前面。他们开始构建一个例子来说明下一步要做什么。他们会检查,在代码还没写之前。(如果写了,那是很特殊个别的情况。)他们编写代码。检查例子是否运行正确,其他例子也保持正确。然后继续下一个例子用于展示下一步应该做的事情。
替换词语有意义吗?是否只是文字上的替换而已?你做一些尝试,然后回答这些问题吧。尝试经常使用“example(例子)”,经常使用让它听起来不会感觉很奇怪。现在,当你坐在代码前面时,是否根本改变了你的观点?是否有了一些不同:在你向客户要求一个例子,而不是一个测试时。加上一些形容词:example(例子)是否看起来更具激发性、更生动、更有深刻内涵?与强大的测试存在怎样的区别?(“强大”作为附加给测试的典型的形容词。)测试人员在XP项目中,每个人都在制作例子,没有人做测试,这样是否看起来更轻松些?