UML软件工程组织

 

 

测试之前的“战略部署”

2008-08-14 作者:陈能技 来源:IT168 

 

测试用例的编写作为QC特定的概念、技能,成为唯一广泛公认的东西。在项目测试过程中,最值得考虑的、最重要的当属测试用例的设计以及创建有效的测试用例。

但是,仍然有不少的测试团队和测试人员认为没有必要编写和设计测试用例,尤其是当敏捷开始盛行后,很多人更是认为编写和设计测试用例是浪费时间。

为什么要写测试用例?

测试用例的创建至少会有两个用途或目的:

(1)如果顾客有要求的话,测试用例会是交付给顾客的产品中的一部分。测试用例在这里充当了提高可信度的作用。

(2)测试用例只作为内部使用。在这里测试效率是目的。在代码尚未完成时,我们基于设计编写测试用例,以便一旦代码准备好了,我们就可以很快地测试产品。

但是随着敏捷的盛行,第二点逐渐受到很多人的置疑。“预先设计好的测试用例对指导测试执行有多大的作用呢?而且我们采用的是探索性测试方法,不写测试用例也能做测试。”

没错,预先写好的测试用例很可能要在测试执行的过程中不断地修改,尤其是在那些需求不明朗的项目中。但是预先的设计就好比提前的探索,除了能学习到软件涉及的业务知识外,还能对即将出现的软件进行一次测试的“演练”,在这个“演练”的过程中,往往能发现需求分析和设计的很多缺陷,将可能由此引致的BUG“扼杀”在萌芽期。

探索性测试虽然很少写正式的测试用例,但是并不意味着没有对测试进行设计。只是测试的设计是在探索过程中、测试过程中进行的,测试的设计与测试的执行同步进行。并且根据Jams Bach介绍的基于Session的探索性测试管理的方法,是要写测试用例的,只不过不被称为测试用例,而是被称为“探索任务”。

基于Session的测试管理把测试过程划分成多个Session,或者叫“探索任务”,每个Session都是目的驱动的,每个Session由一名测试员负责执行,在一个Session结束后,测试员提交一份session报告,附上关于测试过程的重要信息。

“探索任务”可包括如图1所示的任务矩阵中列出的方面。

图1 探索性测试任务

由此可见,探索性测试也有测试的设计,也有测试用例,只是相比起传统意义的测试用例编写而言,其测试用例更偏向于“设计”,并且其设计是与测试执行和探索行为同步进行的。

测试永远也无法保证发现所有的错误。测试用例的“设计”如此重要正是因为完整的测试是不可能的,任何项目的测试都是不完整的,因此,很显然我们需要通过设计测试用例,让测试尽可能的完善。在有限的时间和资源下,测试的关键问题是:哪些测试用例是最有可能发现最多错误的呢?

图2 某个程序的结构流程图

某个程序的结构流程图如图所示,这样一个少于100行Pascal代码的程序,却有100,000,000,000,000种可能的路径需要遍历,如果尝试遍历所有可能的路径,假设每秒钟执行1000个测试用例,也需要3170年的时间来完成所有测试。

详尽地遍历所有测试的可能路径、场景、输入条件和数据是不可能的,因为它们的组合接近无限,但是时间和资源都是有限的。以有限“拼”无限,无异“以卵击石”。因此有些人在这些困难面前妥协了,仅仅使用随机的输入来测试程序,这种测试方式无异“缴枪投降”。

正确的方法是设计合理有效的测试策略,建立合理有效的测试用例库,选择合理有效的测试用例来执行。

测试用例的设计策略

测试用例的设计方法有很多,一般常用的测试用例设计方法有以下几种。

等价类划分法。
边界值分析法。
基本路径分析法。
因果图法。
场景设计法。
错误猜测法。

另外,还有以下几种测试用例设计方法是用于有效减少测试用例个数的。

正交表法。
均匀试验法。
组合覆盖法。

注:关于这些测试用例设计的具体方法,可参考我写的《软件测试技术大全》一书中的第7章。

测试人员为什么要掌握这么多的测试用例设计方法呢?这是因为每一种测试用例设计方法都有其最适合的地方,需要综合应用才能让测试用例的设计省时省力而且能有效发现尽可能多的BUG,另外,交叉使用各种测试用例的设计方法,有助于避免“思维死角”,让BUG“无处遁形”。

最近,日本的测试界比较流行使用思维导图(Mind Maps)工具进行测试用例设计,原因是传统的测试用例设计方法都比较局限在某个区域,缺乏整体业务建模和整体测试逻辑的考虑。而通过“头脑风暴”工具,则可以协助测试人员更全面、更清晰都思考测试涉及的软件功能和业务模型,从而设计和构建出更加完善合理的测试用例。

测试人员通过画出一些关系图、测试对象的相关信息,帮助整理思路,组织内容、想法、创意等。例如,如图3所示的是FreeMind的编辑界面。

图3 FreeMind的编辑界面

类似的还有分类树方法设计测试用例,也是一种测试用例的辅助设计方法。分类树方法的基本原理是:首先把测试对象的可能输入按照不同的分类方式进行分类,每一种分类要考虑的是测试对象的不同的方面。然后把各种分开的输入组合在一起产生不冗余的测试用例,同时又能覆盖测试对象的整个输入域。

因此,可以把使用分类树方法设计测试用例的过程分为3大步骤:

(1)识别出测试对象并分析输入空间。

(2)对测试对象的输入空间进行分类。

(3)画出分类树、组合成测试用例。

图4所示的是利用CTE XL设计分类树并自动产生测试用例的效果。

图4 利用CTE XL设计分类树

不管采用什么样的测试用例设计方法,最重要的是要体现测试人员的逻辑思维,测试用例的设计是测试人员智慧的集中体现,它代表了测试人员对软件的理解,代表了测试人员的测试思路。测试用例的设计是测试人员与软件BUG进行一次歼灭战之前的战略部署,没有一场战争是在毫无准备和计划的情况下赢得胜利的,软件测试也无例外。

测试用例个数代表什么?

Jams Bach在《软件测试经验与教训》一书中打了个形象的比喻来说明测试用例的个数并不代表什么:

如果拿出公司的所有箱子堆起来,并不会知道箱子所装东西的价值。如果公司有37个箱子,总重量是384磅,这能从什么方面说明公司的未来吗?不能。但是这些箱子所装的东西可能和公司的未来是密切相关的。因此要想知道价值所在,唯一的办法就是打开箱子,查看所装的东西。

其实测试用例就像箱子,只是统计箱子个数而不管里面的实际内容的话是没有什么意义的。因此,仅仅统计测试用例的测试通过率也说明不了任何问题。90%的通过率到底是好还是坏呢?如果不了解里面的测试内容的话,谁也不能回答这个问题。

同样地,统计执行得测试用例与计划执行得测试用例的比例也说明不了任何问题。因为也许最难执行的测试用例被推到了最后,或者最后的10%的测试用例需要50%的时间来完成,又或者计划要执行的那些测试用例其实远远不足以覆盖测试的需求,也没有覆盖重要的风险。

因此,衡量一个项目的测试设计是否到位,是否完善,并不能单从所设计的测试用例个数来衡量,还要真正看到测试用例里面的内容。要想让测试用例的个数代表点什么的话,我们必须进行测试用例的评审。

测试用例的评审

测试用例设计出来了,质量如何,如何提高测试用例设计的质量?就像软件产品需要通过各种手段来保证质量一样,测试用例的质量保证也需要综合使用各种手段和方法。

测试用例的检查可以有多种方式,但是最敏捷的应当属临时的同行评审。我认为同行评审,尤其是临时的同行评审,应该演变成类似软件开发中的“结对编程”一样的方式。从而体现敏捷的“个体和交互比过程和工具更有价值”,要强调测试用例设计者之间的思想碰撞,通过讨论、协作来完成测试用例的设计,原因很简单,测试用例的目的是尽可能全面地覆盖需求,而测试人员总会存在某方面的思维缺陷,一个人的思维总是存在局限性。因此需要一起设计测试用例,善用“集体智慧”、“群众的智慧”。

测试用例的评审要点需要至少包括以下几个方面:

  • 测试用例对需求覆盖的完整性。
  • 测试用例的有效性。
  • 测试用例的清晰性。
  • 测试用例的可理解性。
  • 测试用例的可维护性。

除了同行评审,还应该尽量引入用户参与到测试用例的设计中来,让他们参与评审,从而体现敏捷的“顾客的协作比合同谈判更有价值”这一原则。这里顾客的含义比较广泛,关键在于你怎样定义测试,如果测试是对产品的批判,则顾客应该指最终用户或顾客代表(在内部可以是市场人员或领域专家);如果测试是指对开发提供帮助和支持,那么顾客显然就是程序员了。

邀请程序员参与测试用例的评审,就好比临战前的“演练”,测试人员是“剑”,开发人员是“盾”,如果开发人员能回答测试人员基于测试用例提出的所有问题,那么OK,测试人员要好好考虑是否应该增强自己的测试用例了,另外,开发人员回去可能也会好好考虑如何增强自己的程序在处理可能出现的异常和错误方面的代码,真可谓“一举两得”!

当然,在这种开发人员参与的测试用例评审中,也是一个暴露两方对于同一需求的不同理解的机会,通过评审和交流,能尽早达成共识,避免造成在测试执行和BUG修改阶段产生的“误会”。

小结

鼓吹测试用例无用论的测试人员可能并没有真正理解测试用例的意义,没有意识到测试之前进行“战略部署”的重要性,同时也很可能误解了敏捷测试、探索性测试的方法,把自由、随意当成了敏捷,把随机的、即兴的测试当成了探索性测试。

测试用例可粗可细,可建立完善的测试用例库,也可仅仅用一个Excel表来记录,但是一定要对测试进行“设计”,在与软件BUG进行的持续“战斗”中,一定要体现出测试人员的“智慧”来,相信“胸有成竹,则战无不胜”。

 

组织简介 | 联系我们 |   Copyright 2002 ®  UML软件工程组织 京ICP备10020922号

京公海网安备110108001071号