在IT研发领域,个体能力对研发效率的影响很大,个人能力强的开发人员,其工作效率通常要比能力差的高出2~5倍,在特定情况下,差距还甚至扩大到10倍。所以,在软件研发项目中,我们听到项目经理抱怨,几位技术牛人就能决定一个大型产品的成败,为什么将个体成功演进到团队成功就那么难呢?
嵌入式产品的白盒测试是IT研发最难推动的软件过程之一,个人素质对测试效果的影响尤为显著。大家知道,做好白盒测试需要凭借测试工具,但某些优秀员工不依赖工具,仅在代码中插入assert、print语句,也同样把白盒测试做得很好,本文尝试分析白盒测试个体成功的主要因素,以及如何将这些因素规范下来,进行推广到整个组织,引导个人成功走向团队成功。
一、高效测试是推动白盒测试的基本前提
白盒测试之所以难做,瓶颈首先在于测试操作的效率远低于研发进度对它要求。
优秀员工不用测试工具也能做好测试,首先因为他个人习惯保证测试过程是高效的,比如:编程高手总是先理清思路再编码的,编码与写用例都是一次性作业,而普通开发人员是边想边写、边写边调整,少不了有许多反复;再如,高手总是尽可能少做调试,尽量拿测试代替调试,冒出问题常常只看源码就能解决,而刚入门做开发的人,若不在调试器一步步跟踪,他简直要丧失继续生活的勇气;再有,开发高手总喜欢代码写一点测一点,在随时处于稳定的系统中,测出问题与解决问题的效率非常高,而常人更喜欢先把代码写完整再集中做测试,各式各样问题纠缠在一起,定位不容易、解决起来也不容易。
不借助测试工具也可能做好测试,但并不意味着有好工具了也不去用。这里有个误区,通常大家认为写脚本了才算正式测试,其实不是,在被测代码里嵌入一条assert指令,它能反复执行,结果能自动判断,本质上这就是一个测试用例,而且,此形式的用例除了可维护性差些,它的开发效率其实还是很高的,直接重用被测代码的运行过程,用脚本构造测试环境与发起测试都省略了。所以,我们说“高效测试”,而非“使用工具”,是推动白盒测试的基本前提。
有一个指标——测试同比——可以评估嵌入式产品的白盒测试是否有效,测试同比是指保证恒定软件质量的前提下,每新增1千行代码所需的开发投入,与新增测试设计投入之比,前者开发投入主要指:低层设计、编码与调试,后者测试设计投入主要指:编写用例、调试用例。
根据我们的经验数据,测试同比为0.5,即写一天代码要测试两天,表示当前测试效率很低,这时推行白盒测试难逃失败的厄运。测试同比为1,即写一天代码要测上一天,表示测试效率尚可接受,此时白盒测试若有强大的执行力度,比如有良好定义的流程支撑,有完善QA审计把关,该软件过程仍然可以成功,但如果执行力度不足就很容易失败。当测试同比达到2,即写一天代码半天就能测完整,白盒测试就进入良性循环,稍加引导就能促使大家从被动测试转变到主动测试。
如上图,测试同比曲线被划分为3个区间:强制推动区、组织推动区、自发推动区,当测试同比过低,只有不计成本的强制推动才能让白盒测试获得成功,而测试同比提高到2以上,意味着少许投入即获得巨大好处,研发人员不断自测,少曝Bug少挨骂,效率提高了不必天天加班,白盒测试就很容易固化为他们的自发习惯。
在实际操作中,我们常拿上述“分区推动理论”评估一个组织的白盒测试能力,结果与实际情况非常吻合。测试同比为1是拐点,测试效率处于拐点附近白盒测试可以谨慎乐观,但如果远低于拐点,情况就很不妙了。我们遇到过许多产品,尽管产品组对白盒测试非常重视,但他们所遵循的方法论与支撑工具不够高效,或者组织机构欠完善,白盒测试还没开始就已经注定要失败了。
既然测试效率这么重要,我们该如何改善它呢?《第4代白盒测试方法概述》对此有过精辟论述,可以从测试方法与支持工具两个层面去考虑,下面我们列举几个要点:
1. 形式化、脚本化描述测试逻辑有助测试效率提升
2. 在线测试可以大幅提高用例设计、调试与维护的工作效率
3. 把调试操作重用到测试设计,也大幅提高测试效率
4. 持续集成模式让代码稳定性在调试与测试中重用,有力促进整体研发效率提升
二、基于接口规格做测试
白盒测试之所以难做,瓶颈还在于测试效果因人而异,能力强的很容易发现深层次问题,能力弱的或责任心不强的,白盒测试仅是走过场,效果不明显。这里我暂且不论责任心问题,我们主要探讨技术层面,如何保证白盒测试是深入的、是有效的?
对于优秀员工,他设计用例总习惯于回溯规格,因为在动手编码之前,就先已经把规格想清楚了,不管有无形成文档,回溯、检视规格对他来说并非难事。当然,规格有大有小,而且是分层的,在产品层面有产品的特性规格,代码层面有不同层次的接口,比如单元测试,设计用例所依据的规格是被测函数的输入与输出。
对于工作习惯欠佳的员工,编码是边写边想的,想到哪儿就写到哪儿,在他脑中软件规格是模糊的、随意的,而且不断的调整变化。此时让他做单元测试,就很难依据规格去设计用例,其结果不难想象。一方面,代码是他自己写的,他会陷入自身的思维习惯中,另一方面,他只关注当前可见代码,不可见代码(如缺省的else分支、遗漏的处理过程等)被忽略了,我们把这种测试叫做“机械测试”,通俗一点讲,测试者把自身当成器物,比如看出代码有一句“1
+ 1 == 2”,所以设计用例测试1加上1等于2,测试肯定是通过的,覆盖率也能达标,但测试还是没做好,测试者仅承担编译器或lint工具的角色。
在一个组织中,优秀员工与普通员工总是按一定比例存在的,我们很难要求普通员经过简单培训就马上变优秀,所以,让个体成功延伸为组织成功,我们首先考虑在工程方法做改进。极限编程中的测试先行实践(TDD,Test-Driven
Development)可以很好的解决上述问题,TDD要求在编码之前做测试设计,代码尚不可见,先有测试用例,这样无论如何都不会坠入“机械测试”的陷阱了。根据已有文献提供的统计可知,TDD实践总体来说较为有效,但也存在一些固有缺陷,比如在看不到代码情况下先做测试设计,容易让人无所适从。第4代白盒测试方法在实践基础对此做了优化完善,让测试先行(第4代白盒方法中称TDF,Test
Design Firt)很容易操作起来。
三、平稳、持续的以组织行为推进白盒测试
白盒测试若由个体成功延伸为组织成功,还强调该软件过程能持续运作、平稳运行,是标准化可复制的。
首先,我们要解决测试评估问题,以覆盖率评估测试程度是大家熟知的方式,但仅以代码覆盖率做评价就足够了吗?答案是否定的,在商用白盒测试工具中,最常见覆盖标准有3种:语句覆盖、分支覆盖、MCDC覆盖。这些覆盖率指标都反映实际代码中被覆盖的程度,但没有准确反映测试意图的实施程度,也就是说,测试操作中还存在经意测试与不经意测试的区别,为某项测试发起的某个函数调用,可能引发众多子函数层层调用,非关注范围的运行代码也会贡献覆盖率。所以,为了保障测试质量,我们在评估代码覆盖率基础上,还得评估测试设计程度。测试设计程度指标具有统计学意义,它分析测试用例的设计规模,再拿它与被测代码的分支总数作对比。被测代码分支数越多,或代码总量越大,那就应该设计更多的用例来测试它。
其次,严格的白盒测试应从编码开始,一直贯穿于软件产品的整个生命周期,只要代码有修改,测试用例就有补充、维护的需求,所以,白盒测试不是一次过程,而是长期、连续的过程,我们有必要让白盒测试按一种明确的、简要的规则,能持续平稳的向前推进,否则,作为一个组织是很难将白盒测试坚持到底,首次测试比较容易,但增补代码后,白盒测试及时跟进就困难多了。
第4代白盒测试方法在持续集成基础上,要求测试设计在源码修改后立刻跟进,用3个信号灯标识当前被测系统所处的状态,第一个信号灯表示当前测试是否通过,若通过则亮绿灯,否则亮红灯,需要先解决测试问题,第二个信号灯表示当前测试覆盖率是否满足要求,满足了才亮绿灯,否则亮黄灯,需要先改进测试设计,第三个信号灯表示当前测试程度是否满足要求,同样条件满足了才亮绿灯。平稳、持续的推进白盒测试,也就是保证这3个信号灯时常亮起的过程,非绿灯状态是暂态,都要求先解决问题,然后再进入下一轮功能开发。
四、选择一款好工具
推动嵌入式白盒测试是一项系统工程,主要受3个因素影响:人的因素、流程因素、工具的因素,这几个因素相互作用,又互为依赖,真正把白盒测试推行起来难度不小。
前面提到过,一个组织中优秀员工与普通员工总是按一定比例存在的,帕累托的20/80定律反映了众多自然现象与社会现象,在产品运作中也是如此,所有员工中20%是优秀员工,80%是普通员工,优秀员工为研发贡献80%,而普通员工贡献20%,所以,保障一个组织成功推行白盒测试,不必过于倚重人的因素,而更多的应该让流程来规范执行过程,让普通员工也能发挥出接近优秀员工的价值,以及,选择一款好工具,让总体测试效率与测试质量在组织范围内普遍提高。
我们再来分析流程因素与工具因素之间的关系,如果流程很规范,选用测试工具差些,白盒测试仍可推行成功。而同样,如果流程推行不力,但选择的测试工具很好,白盒测试也能成功。评估这两者,我们应识别出哪个因素在本企业更为关键,找出瓶颈问题,有针对性解决了,白盒测试就自然推动起来。
根据经验,目前国内大多数做嵌入式产品的企业没能做白盒测试,其关键原因不在于不想做,或不愿做,而在于缺少一个好工具。软件过程的执行力尚在其次,因为只有一个小组创造了成功case,再推行到其它小组并不困难,操作流程还是容易树起来的。这一点,我们从另一个侧面容易得到验证,比如,近些年来风风火火的持续集成测试、测试先行等实践,在java与C#项目开发中有许多成功案例,但在C++项目成功的就不多,在C项目成功的非常少见,这足以说明:当前白盒测试欠缺的还不是方法论,更多是与方法论相配套的工具。
参考文献:
1. George, B. and Williams, L., "An Initial Investigation
of Test-Driven Development in Industry"
2. ezTester(China),Wayne Chan, 《第4代白盒测试方法概述——理论篇》
3. ezTester(China),Wayne Chan, 《第4代白盒测试方法概述——VcTester实践篇》
4. ezTester(China),Wayne Chan, 《为什么要做白盒测试.doc》
5. Philip M. Johnson, and Joy M. Agustin, "Keeping the coverage
green: Investigating the cost and quality of testing in agile
development"