2005年07月01日

软件测试用例的设计

作者:王静兰

 

一个项目最终呈现在用户面前的质量,与测试执行的程度与力度是密不可分的。测试用例设计的基本目的,是确定一组最有可能发现某个错误或者某类错误的一组测试数据。测试用例构成了设计和制定测试过程的基础,因此测试用例的质量在一定程度上决定了测试工作有效程度。一个好的测试用例使得测试工作的效果事半功倍,并且能尽早的发现一些隐藏的BUG,测试用例的设计是软件开发中的重中之重。

关键词:软件测试,测试用例,TESTCASE,用例设计

A test case is a series of tests used to determine whether one particular thing works properly. Often that means trying the same operation over and over again with little in the procedure.

A test case is a document that describes an input, action, or event and an expected response, to determine if a feature of an application is working correctly. A test case should contain particulars such as test case identifier, test case name, objective, test conditions/setup, input data requirements, steps, and expected results.

 1  引言

1.1  测试用例在软件产品中的作用和意义

软件产品化之后给人们日常生活和工作带来了极大的便利。同样的,也使人们对软件产品的质量重视上升到了更进一步的高度。随着软件危机的不断出现以及人们对于软件更进一步的认识,测试的地位得到了前所未有的提高,并且人们意识到:测试开始的时间越早,软件的缺陷将越早被发现,带来整个软件开发中的成本也下降越多。软件测试是发现软件中缺陷的主要手段和唯一有效的方法。软件质量的重视度越高,软件测试工作在软件开发过程中就越重要。

完全覆盖测试又要求测试工作的力度和深度以及每一种现实中可能发生的操作都要保证正确,很多人觉得这个似乎是矛盾的。软件测试中永远不可能做到穷举测试,又想使得测试工作的效率达到最高,那么该如何兼顾工作量和效率的问题,往往成为测试工作中的瓶颈问题所在。如何测试,用什么方式来测试,在什么环境和什么样的条件下进行测试,测试的工作量和如何避免重复的测试,等等各种应该考虑的因素在测试工作中如何协调和同步,在测试用例中应该充分描述这些问题。

因此,软件测试工作中处于重中之重的测试用例的设计要求也随之上升到了更高的层次。测试用例不但构成了设计和制定测试过程的基础,而且测试的深度与测试用例的数量成正比。一般来讲,判断测试是否完全的一个主要评测方法是基于需求的覆盖,而这个又是以确定、实施和(或)执行的测试用例的数量为依据的;测试工作量与测试用例的数量成比例;测试设计和开发的类型以及所需的资源主要都受控于测试用例。这些使得测试用例在整个的软件开发过程中处于更加重要的地位。

1.2  测试用例的定义

测试用例是为某个特殊目标而编制的一组测试输入、执行条件以及预期结果,以便测试某个程序路径或核实是否满足某个特定需求。

Robert V.Binder是这样描述的,测试实例:输入、执行条件,及为一个特殊目标所开发的预期结果的集合。一个定义IUT(被测实现,即被测代码)及其环境、测试输入或条件,及预期结果的测试前状态的表示或实现。

1.3  测试用例应该包含的要素

首先测试用例应该包含软件或者项目名称、所服务的范围、背景、作者、编写时间等文档类信息;根据测试用例的定义和目的,测试用例的内容应该有:标题和用例编号、版本号、修改记录,针对目标和假设前提/可能发现的错误,输入数据/代码,测试步骤,预期输出和错误发现方法。

1.4  测试用例中需要注意的问题

每个测试用例清楚地阐述了正在进行评估的用例、用例场景、测试目标或条件的有关说明。每个测试用例都描述了预期结果和评估该结果的方法。

对于每个测试需求,在测试用例中需要考虑在正面测试和负面测试的条件下的测试,或者通过确定两个测试用例来实现,一个测试用例代表预期的条件,它可用于核实行为是否正确或符合预期(正面测试)。另一个测试用例代表不可接受的、异常的或意外的条件,它可用于核实测试需求是否未以非预期方式执行(负面测试)。

在一般情况下,对于测试的每个需求来说,至少要有一个正面测试用例和为数较多的负面测试用例,以此来检查在异常情况下系统能否正常处理,或者用户进行了错误的操作时的友好提示等等。

测试用例已被确定用来执行测试目标中所有的产品需求行为,包括(视情况而定): 功能 、数据确认 、业务规则实施 、测试目标工作流程或控制 、数据流 、对象状态 、性能(包括工作量、配置和强度) 、安全性/可访问性 、兼容性。每个测试用例都说明或者/代表一个唯一的输入集或事件顺序,它能够产生唯一的测试目标行为,复审那些产生相同行为的测试用例并判定它们是否等同,即它们是否都执行测试目标中的路径。

每个测试用例(或每组相关的测试用例)确定初始的测试目标状态和测试数据状态。测试用例名称和/ ID 与测试工件命名约定一致。

2  测试用例的设计方法概述

根据测试的方法分为黑盒测试和白盒测试,相应的测试用例的设计方法也可以分为针对黑盒测试的用例设计和针对白盒测试的用例设计。

至今提出的测试用例设计方法有许多,下面简要的介绍一些比较重要的、常用的方法。

2.1  白盒测试的测试用例设计方法

2.1.1 逻辑覆盖

逻辑覆盖包括:语句覆盖、判定覆盖、条件覆盖、判定-条件覆盖、条件组合覆盖、路径覆盖,各自的定义简略描述如下:

语句覆盖就是设计若干个测试用例,运行被测程序,使得每一可执行语句至少执行一次。

判定覆盖就是设计若干个测试用例,运行被测程序,使得程序中每个判断的取真分支和取假分支至少经历一次。

条件覆盖就是设计若干个测试用例,运行被测程序,使得程序中每个判断的每个条件的可能取值至少执行一次。

判定-条件覆盖就是设计足够的测试用例,使得判断中每个条件的所有可能取值至少执行一次,每个判断中的每个分支至少执行一次。

条件组合覆盖就是设计足够的测试用例,运行被测程序,使得每个判断的所有可能的条件取值组合至少执行一次。

路径测试就是设计足够的测试用例,覆盖程序中所有可能的路径。

2.1.2 基本路径测试

基本路径测试方法把覆盖的路径数压缩到一定限度内,程序中的循环体最多只执行一次。

它是在程序控制流图的基础上,分析控制构造的环路复杂性,导出基本可执行路径集合,设计测试用例的方法。设计出的测试用例要保证在测试中,程序的每一个可执行语句至少要执行一次。

2.2  黑盒测试的测试用例设计方法

2.2.1 等价划分

所谓等价类划分是指一套被选择的值,这些值分别代表了许多众多的可能输入值,程序对其处理的方式都是一样的。

等价类划分的方法作为继边界值分析方法之后补充的测试用力设计试用的一种方法。划分等价类、确定测试用例

等价类划分是一种典型的黑盒测试方法,使用这一方法时,完全不考虑程序的内部结构,只依据程序的规格说明来设计测试用例。

等价类划分方法把所有可能的输入数据,即程序的输入域划分成若干部分,然后从每一部分中选取少数有代表性的数据做为测试用例

等价类的划分有两种不同的情况:
有效等价类:是指对于程序的规格说明来说,是合理的,有意义的输入数据构成的集合。

无效等价类:是指对于程序的规格说明来说,是不合理的,无意义的输入数据构成的集合。

在设计测试用例时,要同时考虑有效等价类和无效等价类的设计。

2.2.2 边界值分析

在设计测试用例确定输入和输出参数时,大多数情况下都是用边界值分析方法,采用边界值分析设计的测试用例发现程序错误能力最强。

边界值分析也是一种黑盒测试方法,是对等价类划分方法的补充。

人们从长期的测试工作经验得知,大量的错误是发生在输入或输出范围的边界上,而不是在输入范围的内部。因此针对各种边界情况设计测试用例,可以查出更多的错误。

2.2.3 错误推测法

人们也可以靠经验和直觉推测程序中可能存在的各种错误,从而有针对性地编写检查这些错误的例子。这就是错误推测法。

错误推测法的基本想法是:列举出程序中所有可能有的错误和容易发生错误的特殊情况,根据它们选择测试用例。

2.2.4 因果图

如果程序的功能说明中含有输入条件的组合情况,则一开始就可以选用因果图法。如果在测试时必须考虑输入条件的各种组合,可使用一种适合于描述对于多种条件的组合,相应产生多个动作的形式来设计测试用例,这就需要利用因果图。

因果图方法最终生成的就是判定表。它适合于检查程序输入条件的各种组合情况。

3  测试用例的评审及维护

3.1 测试用例的评审

测试用例在设计之后需要经过评审,需要评审的内容如下:

用例是否完整?是否每一个需求都有其对应的测试用例来验证?

是否每一个设计元素都有其对应的测试用例来验证?

事件顺序,能否产生唯一的测试目标行为?

是否每隔测试用例都阐述了预期结果?

是否每个测试用例(或每组相关的测试用例)都确定了初始的测试目标状态和测试数据状态?

测试用例是否包含了所有单一的边界?

测试用例是否包含了所有的业务数据流?

是否所有的测试用例名称,ID都与测试工件命名约定一致?

测试用例评审时需要参加的人员:项目经理,系统分析员,测试设计员,测试员

3.2  用例库的更新维护

随着软件项目的开发,用例库的数据随着项目的进展动态变化也是需要维护的,主要包括:不合适用例的修改、冗余用例的删除、测试用例的增加,并对进行的操作在备注中署名修改者以及修改时间和改动原因。

4  测试用例实例

该测试案例是以一个B/S结构的登录功能点位被测对象, 该测试用例为黑盒测试用例。假设用户使用的浏览器为IE6.0 SP4

功能描述如下:

1.    用户在地址栏输入相应地址,要求显示登录界面;

2.    输入用户名和密码,登录,系统自动校验,并给出相应提示信息;

3.    如果用户名或者密码任一信息未输入,登录后系统给出相应提示信息;

4.    连续3次未通过验证时,自动关闭IE


4-1登录界面

4-1 登录界面测试用例

用例ID

XXXX-XX-XX

用例名称

系统登录

用例描述

系统登录

用户名存在、密码正确的情况下,进入系统

页面信息包含:页面背景显示

用户名和密码录入接口,输入数据后的登入系统接口

用例入口

打开IE,在地址栏输入相应地址

进入该系统登录页面

 

测试用例ID

场景

测试步骤

 

预期结果

备注

TC1

初始页面显示

从用例入口处进入

 

 

页面元素完整,显示与详细设计一致

 

TC2

用户名录入-验证

输入已存在的用户:test

 

输入成功

 

TC3

用户名-容错性验证

输入:aaaaabbbbbcccccdddddeeeee

 

输入到蓝色显示的字符时,系统拒绝输入

输入数据超过规定长度范围

TC4

密码-密码录入

输入与用户名相关联的数据:test

输入成功

 

TC5

系统登录-成功

TC2TC4,单击登录按钮

 

登录系统成功

 

TC6

系统登录-用户名、密码校验

没有输入用户名、密码,单击登录按钮

系统登录失败,并提示:请检查用户名和密码的输入是否正确

 

TC7

系统登录-密码校验

输入用户名,没有输入密码,单击登录按钮

系统登录失败,并提示:需要输入密码

 

TC8

系统登录-密码有效性校验

输入用户名,输入密码与用户名不一致,单击登录按钮

系统登录失败,并提示:错误的密码

 

TC9

系统登录-输入有效性校验

输入不存在的用户名、密码,单击登录按钮

系统登录失败,并提示:用户名不存在

 

TC10

系统登录—安全校验

连续3次未成功

系统提示:您没有使用该系统的权限,请与管理员联系!

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 参考文献:

[1] 郑人杰,殷人昆,陶永雷,实用软件工程(第二版),清华大学出版社,2001.10

[2] 杨文龙,姚淑珍,吴芸,软件工程;电子工业出版社,1997.11

[3] Robert V.Binder 著,华庆一,王斌君,陈莉 译,人民邮电出版社,2001.4

———————————————————————————–

[作者简介]

姓名王静兰,女,2002年毕业于西安电子科技大学,计算机信息管理专业。

研究方向软件测试管理

Emailpeaceblue2001@163.com    

业余爱好听音乐、爬山

漫谈软件性能测试技术

作者:宣以广

1. 引言

    随着我国加入WTO,各行各业都面临更多的机遇和挑战。如何提高产品的质量,增强市场竞争力,日益成为企业发展必须解决的迫切问题,对软件企业来说尤为重要。软件企业要直接参与国际软件市场的竞争,首要问题就是要保证软件的质量,同时要加快软件产品的发布与交付使用。因此,如何提高软件质量,越来越成为当前软件产业发展中一个迫在眉睫的问题。本文只针对软件质量的性能方面,做一些探讨。

2. 软件质量

    质量保证能力的强弱直接影响着软件业的发展和生存。那么,到底什么是软件的质量呢?《GB/T 16260 信息技术 软件产品评价 质量特性及其使用指南》明确定义:软件质量是软件产品具有满足明确的或隐含需求能力的特征和特性总和。具体包括以下六个方面的质量特性:
1、   功能性
    与一组功能及其指定的性质有关的一组属性。这里的功能是指满足明确或隐含的需求的那些功能。
2、 易用性
    与一组规定或潜在的用户为使用软件所需作的努力和对这样的使用所作的评价有关的一组属性。
3、 可靠性
    与在规定的一段时间和条件下,软件维持其性能水平的能力有关的一组属性。
4、 效率
   与在规定的条件下,软件的性能水平与所使用资源量之间关系有关的一组属性。
5、 可维护性
   与进行指定的修改所需的努力有关的一组属性。
6、 可移植性
    与软件可从某一环境转移到另一环境的能力有关的一组属性。
    因此,为了评价软件产品的质量,需要对软件质量的每个特性实施和执行测试. 随着现代软件构架技术的发展,特别是WEB技术的发展,与软件可靠性、效率质量特性相关的软件性能问题越来越受到包括软件从业人员、专家学者以及软件使用者的重视,软件的性能指标的好坏已直接影响到软件的质量。

3. 软件性能测试技术

    软件性能的测试一般包括三个方面,即性能评测、负载测试和强度测试。每一方面的测试都有其不同的测试目标、测试技术、完成标准,具体如下:

3.1 性能评测

    针对响应时间、事务处理速率和其他与时间相关的需求进行评测和评估。目标是验证性能需求是否都已满足。
测试目标
验证所指定的事务或业务功能在以下情况下的性能行为:
    (1)   正常的预期工作量
    (2)       预期的最繁重工作量
测试技术:
使用为功能或业务周期测试制定的测试过程。
    (1)通过修改数据文件来增加事务数量,或通过修改脚本来增加每项事务的迭代数量。
    (2)脚本应该在一台计算机上运行(最好是以单个用户、单个事务为基准),并在多个客户机(虚拟的或实际的客户机)上重复。
   完成标准:
    (1)单个事务或单个用户:在每个事务所预期或要求的时间范围内成功地完成测试脚本,没有发生任何故障。
    (2) 多个事务或多个用户:在可接受的时间范围内成功地完成测试脚本,没有发生任何故障。
注意事项:
综合的性能测试还包括在服务器上添加后台工作量。 可采用多种方法来执行此操作,其中包括:
    (1)直接将“事务强行分配到”服务器上,这通常以“结构化查询语言”(SQL) 调用的形式来实现。
    (2) 通过创建“虚拟的”用户负载来模拟许多个(通常为数百个)客户机。此负载可通过“远程终端仿真”(Remote Terminal Emulation) 工具来实现。此技术还可用于在网络中加载“流量”。
    (3) 使用多台实际客户机在系统上添加负载。
    (4) 性能测试应该在专用的计算机上或在专用的机时内执行,以便实现完全的控制和精确的评测。
    (5) 性能测试所用的数据库应该是实际大小或相同缩放比例的数据库。

3.2 负载测试

    负载测试通过使测试对象承担不同的工作量,以评测和评估测试对象在不同工作量条件下的性能行为,以及持续正常运行的能力。目标是确定并确保系统在超出最大预期工作量的情况下仍能正常运行,以及软件的性能特征,例如,响应时间、事务处理速率和其他与时间相关的方面。
测试目标:
    验证所指定的事务在不同的工作量条件下的性能行为时间。
测试技术:
    使用为功能或业务周期测试制定的测试。通过修改数据文件来增加事务数量,或通过修改测试来增加每项事务发生的次数。
完成标准:
    多个事务或多个用户:在可接受的时间范围内成功地完成测试,没有发生任何故障。
注意事项:
    (1)负载测试应该在专用的计算机上或在专用的机时内执行,以便实现完全的控制和精确的评测。
    (2) 负载测试所用的数据库应该是实际大小或相同缩放比例的数据库。

3.3 强度测试

    强度测试目的是找出因资源不足或资源争用而导致的错误。如果内存或磁盘空间不足,测试对象就可能会表现出一些在正常条件下并不明显的缺陷。而其他缺陷则可能由于争用共享资源(如数据库锁或网络带宽)而造成的。强度测试还可用于确定测试对象能够处理的最大工作量。
测试目标:
验证测试对象能够在以下强度条件下正常运行,不会出现任何错误:
    (1) 服务器上几乎没有或根本没有可用的内存(内存和磁盘空间)
    (2)  连接或模拟了最大实际(实际允许)数量的客户机
    (3) 多个用户对相同的数据或账户执行相同的事务
    (4) 最繁重的事务量或最差的事务组合
注:强度测试的目标可表述为确定和记录那些使系统无法继续正常运行的的情况或条件。
测试技术:
    (1)  使用为性能评测或负载测试制定的测试。要对有限的资源进行测试,就应该在一台计算机上运行测试,而且应该减少或限制服务器上的内存和磁盘空间。
    (2)  对于其他强度测试,应该使用多台客户机来运行相同的测试或互补的测试,以产生最繁重的事务量或最差的事务组合。
完成标准:
    所计划的测试已全部执行,并且在达到或超出指定的系统限制时没有出现任何软件故障,或者导致系统出现故障的条件并不在指定的条件范围之内。
注意事项:
    (1)  如果要增加网络工作强度,可能会需要使用网络工具来给网络加载消息或信息包。
    (2)  应该暂时减少用于系统的磁盘空间,以限制数据库可用空间的增长。
    (3)  使多个客户机对相同的记录或数据账户同时进行的访问达到同步。

4. 结束语

    软件质量的保证,不仅需要科学的测试策略,更要处理好整个软件生命周期中其他如需求、分析、设计、实现各阶段中出现的问题。只有对软件质量进行全面、全过程的质量控制,才能最终保证软件产品的质量,提高企业的竞争力。

感悟测试驱动开发

来自:天极论坛 作者:徐峰
      软件开发方法学的泰斗Kent Beck先生最为推崇"模式、极限编程和测试驱动开发"。在他所创造的极限编程(XP)方法论中,就向大家推荐"测试先行"这一最佳实践,并且还专门撰写了《测试驱动开发》一书,详细说明如何实现。测试驱动开发是极限编程的重要特点,它以不断的测试推动代码的开发,从而实现既简化代码,又保证质量的目标。
  一看到"测试先行"、"测试驱动"这样的名字,就深深地激起了我强烈的好奇心,开始了自己的探索之旅..

1. 心灵震憾

      一段时间的学习,让我的内心受到了深深的震撼。我们原来的方法居然如此的笨我面对测试先行这一名字时,当时最大的疑问就是"程序都还没有写出来, 测试什么呀!"。后来一想,其实这是一个泥瓦匠都明白的道理,却是自己在画地为牢。我们来看看两个不同泥瓦匠是如何工作的吧:
        工匠一:先拉上一根水平线,砌每一块砖时,都与这根水平线进行比较,使得每一块砖都保持水平。
  工匠二:先将一排砖都砌完,然后拉上一根水平线,看看哪些砖有问题,再进行调整。
  你会选择哪种工作方法呢?你一定会骂工匠二笨吧!这样多浪费时间呀! 然而你自己想想,你平时在编写程序的时候又是怎么做的呢?我们就是按工匠二的方法在干活的呀!甚至有时候比工匠二还笨,是整面墙都砌完了,直接进行"集成测试",经常让整面的墙倒塌。看到这里,你还觉得自己的方法高明吗?
  单元测试长期以来被忽视
  每一个程序员都知道应该为自己的代码编写测试程序,但却很少这样做。当人们问为什么的时候,最常听到的回答就是:"我们的开发工作太紧张了"。但这样却导致了一个恶性循环,越是没空编写测试程序,代码的效率与质量越差,花在找Bug、解决Bug的时间也越来越多, 实际效率大大降低。由于效率降低了,因此时间更紧张,压力更大。你想想,为什么不拉上一根水平线呢?难道,我们不能够将后面浪费的时间花在单元测试上,使得我们的程序一开始就更加健壮,更加易于修改吗?抛弃原来的托词吧!
  我们的自动化水平太低了
  有人还会解释说,那是因为拉根水平线很简单,而写测试程序却是十分复杂的。我暂且对这句话本身不置可否。不过也体现了一个新问题,我们需要更加方便、省时的编写测试程序的方法。
  要测试一个类,最简单的方法是直接在调试器中使用表达式观察对象的值与状态,你也可以在程序中加上一些断言、打印中间值等,当然还可以编写专门的测试程序。但是这些方法都有一个很大的局限性,都需要加入人工的判断和分析。
  由此,自动化测试的引入才是解决之道。正是因为如此,提倡"测试驱动开发"的人群,开发出一系列的自动化单元测试框架xUnit,现在已经有针对Java、Pyhton、C++、PHP等各种常用语言的测试框架。这足以搪塞住那些以"编写测试代码太麻烦"为理由的开发人员,让他们没有理由逃避单元测试。
  正如Robert Martin所说:"测试套件运行起来越简单,就会越频繁地运行它们。测试运行越多,就会越快地发现和那些测试的任何背离。如果能够一天多次地运行所有的测试,那么系统的失效时间就决不会超过几分钟"。

2. 认清测试驱动开发

      测试驱动开发理论最初源于对这些问题的思考:
  1)如果我们能够在编写程序代码之前先进行测试方案的设计,会怎样?
  2)如果我们保证除非没有这个功能将导致测试失败,否则就不在程序中实现该功能,会怎样?
  3)换一个角度,如果当测试时发现必须增加某项功能才能够通过测试时, 我们就增加这一功能,会怎样?
  大师们通过带着这些问题的实践, 发现这的确是一个提高软件代码质量, 使得效率得到保障的一个很好出发点。
       以这样的思路进行软件开发,可以保证程序中的每一项功能都有测试来验证它是正确的,而且每当功能被无意修改时, 测试程序会发现。同时,也使我们获得了一个新的观察点,从对程序调用者有利的视角来观察我们的程序,这使得我们在关心程序功能的本身还能够对接口予以足够感悟测试驱动开发的关注,使得其更容易被调用。另外,这种思路下的代码,将变得更加易于调用,也就必须使其与其它代码保持低耦合性。并且,当你想复用这些模块时,测试代码给出了很好的示例。这一切,使得软件开发工作的质量一下子变得有保障了。
  因此,测试驱动开发的精髓在于: 将测试方案设计工作提前,在编写代码之前先做这一项工作; 从测试的角度来验证设计,推导设计; 同时将测试方案当作行为的准绳,有效地利用其检验代码编写的每一步,实时验证其正确性,实现软件开发过程的"小步快走"。

3. 实践测试驱动开发

      下面,我就结合一个实际的小例子,来说明如何进行"测试驱动开发"。本实例在J2SE SDK 1.4.2环境下开发,以及配套工具JUnit 3.8.1。
  任务简述
  队列是一种在程序开发中十分常用的数据结构,在此我就以编写一个实现队列功能的类–Queue为例进行说明。该类将实现以下基本运算:
  判断队列是否为空:empty()
  插入队列(即在队列未尾增加一个数据元素):inqueue(x)
  出队列(也就是将队列首数据元素删除):outqueue()
  取列头(也就是读者队列首数据元素的值):gethead()
  清空队列(也就是将队列的所有数据元素全删除): clear()
  查询x在队列中的位置:search(x)
  测试案例分析
  在测试驱动开发实践中,第一步就是考虑测试方案,通过分析该类的功能,我们可以得到以下测试案例:
  1) 队列为空测试
   TC01: 队列新建时,应为空;
   TC02: 清空队列后,应为空;
      TC03: 当出队列操作次数与插入队列操作次数一样时,应为空;
  2) 插入队列测试:
   TC04: 插入队列操作后,新数据元素将插入在队列的未尾;
   TC05: 插入队列操作后,队列将一定不为空;
  3) 出队列测试
   TC06: 出队列操作后,第一个数据元素将被从队列中删除;
   4) 取队头测试
   TC07: 取队头操作将获得队列中的第一个数据元素。
  5) 清空队列测试
   TC08: 清空队列操作后,队列将为空队列;
  注: 此处为了讲解的方便,并未将所有的测试用例都列出,同时也选择了一些         十分简单的测试用例。
  第一次迭代
  我们首先编写第一个测试代码,这一测试代码只考虑了测试案例TC01, 也就是保证新建的队列为空:
       安装JUnit十分简单,只需在www.junit.org中下载最新的软件包(ZIP格式), 然后将其解压缩,并且将"JUnit安装目录\junit.jar" 以及"JUnit安装目录"都加到系统环境变量CLASSPATH中去即可。
  执行套件可以像上述程序一样在main方法中使用,也可以直接在命令行调用:java junit.textui.TestRunner 测试类名(文本格式)、java junit.awtui.TestRunner 测试类名(图形格式,AWT版)、java junit.swingui.TestRunner测试类名(图形版,Swing版)。
  编译执行(即在命令行执行javac testQueue.java和javatestQueue), 你会发现屏幕上出现提示:
  .E 一个小点说明执行了一个测试用例,E表示其失败
  Time: 0.11 说明执行测试共花费了0.11秒
  There was 1 error: 说明存在一个错误
  1) testEmpty(testQueue)java.lang.NoClassDefFoundError: Queue
    at testQueue.setUp(testQueue.java:13)
    at testQueue.main(testQueue.java:9)
  FAILURES!!!
  Tests run: 1, Failures: 0, Errors: 1
  测试没有通过是肯定的,因为Queue类都还没有写呢?怎么可能通过测试,因此,我们就编写以下代码,以使测试通过:
 
将这个类编译后,再次执行测试程序,这时将出以下提示:
  . 一个小点说明执行了一个测试用例,没有E表示其成功
  Time: 0.11
  OK (1 test)
  你还可以使用前面我们说到的另两个命令,使测试反馈以图形化的形式体现出来,例如,执行java junit.awtui.TestRunner testQueue, 将出现:
3-1
第二次迭代
  接下来,我们修改测试程序,加入测试案例TC04、TC05的考虑。
  
 根据这个测试代码,我们需要在Queue类中添加上inqueue() 和search() 两个方法,如下所示:
 
 
  编译之后,再次执行java junit.awtui.TestRunnertestQueue, 你将再次看到成功的绿色。
3-2 运行成功状态
       我们仔细看一下这一界面。
  1) 最上面列出了测试代码的类名,右边有一个"Run" 按钮,当你需要再次运行这一测试代码时,只需单击这个按钮。另外,将"Reload classesevery run" 选项打上勾很有用,当你测试未通过(出现红色时), 你可以转身去修改代码,修改完后,只需再按"Run" 按钮就可以再次运行。
  2) 中间区域是一个状态汇报区,红色表示未通过,统计了共运行了多少个测试(也就是在TestCase类中方法的数量)。
  3) 如果测试时出现错误,例如,我们不小心将"assertTrue(!(q2.empty()));" 误写成为"assertTrue(q2.empty());" 就将造成测试失败:
  注:由于第一个测试还是通过的,因此你会看到绿色条一闪。这时,你将会发现JUnit会将错误列出来,并且对应的"Run"按钮也由灰变成了亮,这表示你可以转身修改,完成后单击这个"Run按钮"可以只做刚才失效的这个测试,这将节省大量的时间。
  同时,在最下面的窗体里,列出了失效的详细原因。
3-3 失败的状态
后面的迭代
  到这里,开发还没有完成,但这种思想却已经通过这样两个短小的实践传递出去了,后面的活大家可以动手试一下。
  另外值得一提的是,这里虽然洋洋洒洒一大篇,实际两次迭代花费了我不到15分钟就完成了。而且,当看到绿条时,心里十分舒畅。

4. 一些遗憾

        文章到此就告一段落,但却有些许遗憾。
  遗憾之一:这只是一篇文章,没有办法把所有方面都讲得面面俱到,以致于大家可能无法马上上手。
   正是由于这样的原因,本文取名为"感悟", 与大家交流一下体会,希望能够帮助大家更好地接受"测试驱动开发"的理念,并开始着手实践。
  遗憾之二:笔者水平有限,无法解决大家的各种问题。
  让笔者感到欣慰的是,记载着这些答案的《测试驱动开发》、《敏捷软件开发》、《拥抱变化: 解析极限编程》等大作都已悉数摆上了中国的书店。路虽难走,但明师已有。
  实践永远是学习的最好方法,看到笔者的感悟,就开始极限之旅吧,因为那里风光无限,乐趣无限。当你掌握了测试驱动开发的精髓,那你就能够对你自己编写的所有代码充满信心,不再担心它们什么时候在你的后面放一冷箭,从此告别这给你带来无限压力的苦恼。

ClearQuest体系结构分析

作者: pyp
 
关键字   ClearQuest、 体系结构分析 
    这一段时间,一些人问了我很多关于CQ的问题,我想其中的很多问题都是由于对于CQ的整体结构不熟悉造成的,所以写了这篇文章,希望能对大家更深入的了解CQ有所帮助。我使用的CQ版本是2002.05.00,谁知道哪里能下载2003版的,我一直想看看2003和2002有什么差别。
    ClearQuest是按照标准的三层结构设计的,包括数据层、功能层(业务层)、表示层。下面分别说明三层的构造和相互的关系。

1、数据层

    ClearQuest的根本在数据库,所有的内容都储存在数据库中。在使用CQ数据库的时候,一定要记住一点:必须先建立空白的数据库再进行CQ的操作。因为除非使用Access数据库,其他类型数据库都涉及数据库操作权限的问题,所以必须先建立操作数据库的角色。
    CQ的数据库层分为两种,一种是Maintenance Tool中Schema Repository使用的数据库(下面简称SR数据库);另外一种是Desiger中Schema使用的数据库(下面简称S数据库)。

1.1 SR数据库

    SR数据库中存储了Schema Repository信息以及附属的Schema信息。如果原先没有SR数据库,在Maintenance Tool中通过Create建立Schema Repository和SR数据库的连接,Schema Repository内容储存在SR数据库中。如果原先存在SR数据库,在Maintenance Tool中通过New Connection建立Schema Repository和原有SR数据库的联系,原有SR数据库内容不变。SR数据库中,不只存储了Schema Repository,还包括Schema Repository附属的Schema信息以及User Adminitrator中的Group和User信息。删除Schema Repository的时候,SR数据库仍然存在,随时可以通过New Connectio连接回来。Move SR数据库的时候,源SR数据库仍然存在,随时可以通过New Connectio连接回来。

1.2.R数据库

    R数据库对应相关的Schema信息,包括Schema本身的各种信息、用户通过客户端录入的变更信息(Defect、Email_Rule、Project等)、操作此Schema的Groups和Users信息。删除Schema的时候,R数据库仍然存在,随时可以通过New Connectio连接回来。Move R数据库的时候,源R数据库仍然存在,随时可以通过New Connectio连接回来。

2、功能层

    功能层是CQ中最重要的,所有的设置几乎都在功能层实现。功能层包括两个部分,Maintenance Tool和Designer。还有一个可选择配置的Web服务器。下面分别进行说明。

2.1.Maintenance Tool

    Maintenance Tool(安装目录中cqdbsetup.exe)是在使用CQ前必须配置的。在Maintenance Tool中,必须Create或New Connection至少一个Schema Repository。无论是Designer、客户端还是Web服务器最后都必须连接Maintenance Tool中的Schema Repository。Schema Repository按照字面的翻译是“计划仓库”,也就是说,所有的Designer中的Schema都附属于特定的Schema Repository。如果有多个Schema Repository,在使用designer、客户端、Web服务器的时候,必须选择特定的Schema Repository,之后的操作都在此Schema Repository中进行。Schema Repository实际是一个连接SR数据库并把相应数据记载到SR数据库的行为。

2.2.Desinger

    Desinger(安装目录中的cqdesign.exe)是设计Schema使用的。在进入Desinger的时候,如果Maintenance Tool中有多个Schema Repository,必须选择一个Schema Repository才能进入Desinger,此时在Desinger中设计的所有Schema都附属于此登陆的Schema Repository,并且所有Schema信息都储存于对应的SR数据库中。Designer中的Schema是可以独立存在的,不一定非要连接S数据库,因为Schema的信息存储在SR数据库中。不过如果想在客户端或Web端使用Schema及其相关内容,则必须建立和Schema相对应的S数据库。
    新建Schema是一个继承的过程,必须选择一个原有的Schema,继承原有Schema所有的Field、States and  Actions、Forms等内容。所以可以建立一个配置好的标准Schema(不用连接数据库),所有其他的Schema都从此标准Schema中继承,进行简单的修改就可以使用了。
    Schema连接的S数据库分为两种:Production Database和Test Database。Test Database是为Schema设计的时候使用的,设计好后,如果建立了Schema对应的Test Database,则可以选择菜单中的File->Test Work调用客户端查看Schema设计的结果,此过程可以反复进行,相当于调试的过程。Production Database是实际使用的数据库。只有存在Production Database的时候,才可以在实际使用客户端访问的过程中看到相应的Schema。菜单Tools->User Adminitrator里面设置Group和User,此User不只在CQ中使用,Robot等User也都调用CQ中设置的User。

2.3.Web服务器

    如果想在Web端使用CQ,就必须配置Web服务器,否则可以不安装或配置Web Server Components。在设置Web的时候,如果是NTFS格式的文件分区,一定要设置Cache目录的完全控制权限,我看到很多人的问题都出在这里。

3、表示层

    CQ可以使用两种方式访问:Web端browser访问或客户端访问。

3.1.Web端访问

    如果想Web端访问,则必须配置Web服务器。

3.2.客户端访问

  客户端(安装目录中clearquest.exe)是实际进行变更流程操作的CQ访问程序。在客户端,可以建立Query、Chart、Report等。客户端通过建立的Query才可以看到提交的记录。Report的使用,必须有相应的水晶报表企业版。Email_Rule(邮件规则)在客户端设置。

4、其他工具

    在CQ中,还有其他的一些工具,下面进行简略的说明。

4.1.Export Tool、Import Tool

    这两个个工具我感觉用途是在不同的Schema中导入导出数据。比如一个Schema用完后,下一个Schema希望能把上一个计划未处理的记录导入到新记录中,就可以使用这两个工具了。工具使用比较的麻烦,关键的是必须设置每一个Field的对应关系,为此不得不把两个Schema的Field弄成一样。

4.2.Create Rational ClearQuest Evaluation Databases

    此工具就是在固定的目录创建一个Access数据库的Schema Repository,感觉一点用处都没有。

4.3.ISQL、Sybase Cetral

    这个两个工具好像是给数据库为Sybase的时候使用的。我没有使用过Sybase数据库,所以不很了解这两个工具的使用。
2005年06月29日

点评性能测试工具OpenSTA.

作者: 缑萍萍
关键字:性能测试,测试工具,OpenSTA
 
摘要:
    本文将介绍一个免费的、源代码开放的web性能测试工具OpenSTA,包括它的原理、组成部分、录制脚本的过程。另外,还将介绍如何在OpenSTA的测试脚本中引入变量,并给变量赋不同值,比如,将登陆被测试网站的用户名称设置为一个变量,在执行性能测试时,虚拟多个不同的用户同时登陆被测试网站,通过将访问网站的用户名称打印出来的方法,验证该变量在测试执行过程中被赋与了不同值。
 
正文:
    作为测试工程师,不能只关注系统的功能,还必须对系统的性能进行全面的测试,才能确认系统是否满足用户的需求。那么什么是性能测试呢?
    “中国软件评测中心将性能测试概括为三个方面:应用在客户端性能的测试、应用在网络上性能的测试和应用在服务器端性能的测试。应用在客户端性能测试的目的是考察客户端应用的性能,测试的入口是客户端。它主要包括并发性能测试、疲劳强度测试、大数据量测试和速度测试等,其中并发性能测试是重点。”(《性能测试:软件测试的重中之重》作者:中国软件评测中心 发文时间:2003.08.26) 
    目前比较著名的并发性能测试工具有Rational Robot、QALoad、LoadRunner和微软的WAS等。这其中QALoad、LoadRunner、Rational Robot都是比较不错的商业测试工具(价格也很贵哦),微软的WAS是一个免费的测试工具,使用起来比较简单,但是由于不能显示和编辑所录制的测试脚本,其可控性和图形化测试结果都较弱,故造成一定的局限性。
    OpenSTA是专用于B/S结构的、免费的性能测试工具。它的优点除了免费、源代码开放的优点外,还能对录制的测试脚本进行,按指定的语法进行编辑。测试工程师在录制完测试脚本后,只需要了解该脚本语言的特定语法知识,就可以对测试脚本进行编辑,以便于再次执行性能测试时获得所需要的参数,之后进行特定的性能指标分析。OpenSTA以最简单的方式让大家对性能测试的原理有较深的了解,其较为丰富的图形化测试结果大大提高了测试报告的可阅读性。
    OpenSTA是基于Common Object Request Broker Architecture (CORBA)的结构体系。它是通过虚拟一个proxy, 使用其专用的脚本控制语言,记录通过proxy 的一切HTTP/S traffic。测试工程师通过分析OpenSTA的性能指标收集器收集的各项性能指标,以及HTTP数据,对被测试系统的性能进行分析。
    首先,OpenSTA都有哪些组成部分?
u   OpenSTACommander – 主要控制应用程序;
u   NameServer – CORBA背景处理器,保证OpenSTA各个组成部分之间的交流;
(NameServer是安装OpenSTA的同时被安装的,正常运行时,可以在Windows任务栏的右侧看到图标 ,如果没有正常运行或者被停止了,图标显示为 。)
u   ScriptModeler – 配置、启动HttpGateway的工具程序,同时也是录制脚本的工具程序;
u   HttpGateway – 模拟proxy 处理器,执行录制;
(接受用户手工配置的proxy设置,不接受任何自动配置proxy机制);
u   TestExecuter – 真正执行测试的背景处理器;
u   WebRelayDaemon  –使用XML RPC在internet上过滤 CORBA限制;
u   Repository–测试脚本、配置和测试结果存贮目录;
u   TestManager–管理测试运行的背景程序;
u   TaskGroupExecuter–运行TaskGroup的处理器。
    其次,什么是性能指标收集器(即Collector)呢?这是用户定义的一组问题,决定在测试过程中哪些性能指标需要记录。包括两种类型:
1)NT Performance Collectors 用于采集运行WinNT或Win 2000的主机的性能指标.
2)SNMP Collectors 用于采集主机和其他运行 SNMP agent 或 proxy SNMP agent的SNMP数据.
Collector的设置将在下面如何录制测试脚本中介绍。
 
    第三,如何录制测试脚本呢?
1、    安装OpenSTA后,在“程序”中出现OpenSTA的三个工具程序,如下图:
1-1安装后的界面
    检查OpenSTA NameServer状态为运行中,即图标为
 
    运行“OpenSTA Commander”,界面显示为下图:
1-2运行后的界面
2、录制新脚本
    1)鼠标点“Scripts”,通过右键菜单“New Script”->“HTTP”生成新脚本,脚本名称缺省为NEWSCRIP(如下图);
1-3脚本界面
    2) 双击新脚本,打开Script Modeler窗口,在Options菜单中设置Browser和Gateway,一般情况下,保持Gateway的缺省设置 ;
1-4录制脚本界面
    3)按工具栏中的红色圆钮,自动打开指定的浏览器,输入需要录制的系统URL, 显示被测试网站的首页内容。在登陆成功之后,执行各个既定的操作步骤。按工具条上的方框按钮,或直接退出浏览器,可以停止脚本的录制,这是在Script Modeler窗口中将看到被录制下来的脚本语句。
 
3、生成Collector
    1)    鼠标点“Collectors”,通过右键菜单生成新指标收集器,缺省为NEWCOLLECTOR;
1-5生成收集器
    2)    通过browse Queries浏览并设置需要收集的性能指标。(各个性能指标的含义不是这篇文章所包含的内容,这里不做介绍)
 
4、   组成测试环境
    与脚本和性能收集器同样的方法,在Tests中新建一个NEWTEST(下图中已将新建的Test进行了重新命名), 将测试脚本和性能指标收集器拖到该Test中,如下图;
1-6 测试环境界面
5、   按工具栏中的 ,执行测试,测试过程中可以查看“Monitoring”页签的内容,测试结束后,该页签为空;
6、   测试结束后,点工具按钮下方的Results页签,显示所记录的测试结果数据,如下图。
1-7 测试结果界面
    至此,读者对如何使用OpenSTA这个测试工具应该有了一个大概的了解,如果需要详细了解使用的细节,可以查看该工具的使用手册,不过是E文的哦:)。需要下载OpenSTA工具的朋友可以访问网站http://www.opensta.org/,使用手册也可以在这个网站上下载。

    下面,介绍如何在OpenSTA的测试脚本中引入变量,并给变量赋不同值的过程。网络应用系统一般都会有一个登陆网页,需要用户输入正确的用户名称和密码,经过系统验证后,用户才能进入该应用系统。在使用OpenSTA录制测试脚本时,输入的用户名称和密码将被OpenSTA记录在脚本中,录制完成后,可以在脚本文件中发现如下语句:

 这里“mike”、“ekim”就是录制脚本时登陆系统所输入的用户名称和密码。

  问题是在执行性能测试时,往往需要模拟很多个不同的用户同时登陆系统,观察系统的各项性能指标。为每个不同的系统用户录制单独的测试脚本是不现实的。那么,如何修改已录制好的测试脚本,使其在测试过程中可以模拟多个不同的虚拟用户,而每个虚拟用户的用户名称和密码都被写入测试脚本中呢?
 
1、首先,在测试脚本的Definition部分中增加变量USERNAME、PASSWORD的定义:
这里假设mike、allan、david、robert是该系统正确的用户名称,ekim、nalla、divad、trebor分别是这些用户的登陆密码
(说明:OpenSTA测试脚本分三个部分, Environment、Definition、Code)
2、同时,在脚本的Definition 部分增加变量MY_USERNAME、MY_PASSWORD的定义:
CHARACTER*512 MY_USERNAME, LOCAL
    CHARACTER*512 MY_PASSWORD, LOCAL 
(注意,这两个变量范围是LOCAL型)
3、在发送登陆请求的语句“PRIMARY POST URI"http://demosite.opensta.org/gsg-v1 HTTP/1.0"ON 2…….”之前, 添加下列语句:
ACQUIRE MUTEX "LOGIN"
   NEXT USERNAME
   NEXT PASSWORD
   SET MY_USERNAME = USERNAME
   SET MY_PASSWORD = PASSWORD
RELEASE MUTEX "LOGIN"
其中:
AQUIRE MUTEX命令 的含义是: 将变量USERNAME 和PASSWORD 设置为用户名称和密码这两个变量选择值序列中的第一个值,并设置为local 形式,避免其他虚拟用户使用这个值;
RELEASE MUTEX命令 的含义是:释放Mutex, 其他虚拟用户可以选择序列中的第一个值(序列中的值是被循环使用的);
    这里需要解释一下MUTEX锁定机制 的含义,是为了避免多个虚拟用户测试时,自动从变量选择值序列中进行选择时,出现选择同一值的现象(即选择了同一个用户的现象);
4、将发送登陆请求的PRIMARY POST语句中BODY的用户名和密码替换成变量:
    至此,对测试脚本的修改已经完成。按照本文前面所介绍的OpenSTA操作步骤,设置性能测试收集器,设置虚拟用户的个数为4,开始执行测试,OpenSTA就会模拟mike、allan、david、robert这4个不同的用户同时登陆系统的情况。说到这里,读者可能又会问,怎么验证在测试执行过程中,确实是模拟了这几个用户进行登陆的呢?我们可以通过将所有登陆系统的用户名称打印出来的方法进行验证。
方法是,在发送登陆请求的PRIMARY POST语句之后,添加Report语句:
REPORT  "USER ", MY_USERNAME
这样在测试执行完成后,Test Report Log中就可以看到打印出来的登陆用户名称。(是不是很简单?大家可以来试试)
作者在自己的测试脚本中进行实验,设置虚拟用户为3个,在登陆请求语句之后增加Report语句,以下是测试结束后Test Report Log信息
1-8 测试结果
这里,“admin”、“sjcj”、“data”是被测试系统的三个用户名称。
通过上边的一系列阐述,大家对Web性能测试工具OpenSTA应该有了一定的了解。如何更有效的利用这个工具,收集系统的性能指标进行性能分析,希望大家共同探讨。
 
参考文献:
1.OpenSTA user manual
----------------------------------------------------------------------------------------------
[作者简介]
姓名:缑萍萍:女,在软件行业有将近10年的经历,前后从事过技术支持、C++软件开发、流程管理和软件测试的工作,期间在英国攻读完工程管理的硕士学位。至今,已经做了1年多的web应用系统软件测试工作,对这个工作非常有兴趣,也小有一些心得。测试行业在国外已经发展的比较成熟了,在国内这几年才逐渐引起重视,作者希望能够通过自己的努力将国外先进的技巧、理念引入国内,与国内同行共同交流,以快速提高我国的软件测试水平。

软件测试自动化实践

作者:chris

    首先为什么需要软件测试自动化?通过我这几年在微软的工作,可以感觉到一点,应该说自动测试,可以定义软件系统。从理论上来说应该是功能定义软件系统,软件系统是怎么工作的是从功能规格上来看的。但是你要是没有一套可以自动测试的测试程序存在,就没有办法验证我这个软件系统,就是修改了一点点,这个软件系统是不是和前面的软件系统一模一样,你没有办法验证,只有有一套自动系统,才能验证软件系统是不是还在原来的状态上。我觉得自动测试是非常重要的一个东西,微软一个软件系统如果没有跟着一套自动系统的话,这个软件系统基本上没有生命力,也没有办法进行更新,其他的各式各样的服务也没有办法进行。
    代码的复杂性也是不能小看的。现在测试一个代码时,所有的覆盖也是不可能的事情,每一个if…else…或switch语句就会把情况增加一倍,许多异常处理代码正常使用中不会碰到。许多与时序,死锁,资源冲突,多线程有关的错误很难捕捉到。除此之外,我们每一个版本又各自带SP与QFE,每个SP进 行组合,可以得到一个天文数字,如果没有一个自动测试系统的话,要测试整个产品,在所有不同的情况下进行工作的话,几乎是一个不可能的事情。你要是有一套自动测试系统,对未来 会有一种事半功倍的效果。
    微软内部有各种不同的测试,首先开发团队有自己的DRT或者Check-in Suites。不需要重装机器,要求速度快,对结果汇报要求简单,100%通过就行,所以不需要很强的分析的能力。与开发团队的关系近,在他们的源代码控制系统中。测试团队有测试的Lab BVT,所有的测试者都是在一起的,BVT的要求是需要重新安装机器,可以排除其他老的因素在上面的干扰。要求速度快,只运行0级测试,BVT也是在每天的构建结束以后自动运行BVT,结果汇报要求也是比较简单,一般来说需要100%,如果不是100%总是要找问题,前天的结果,大前天的结果应该都是100%。与测试团队的关系近,在测试团队的源代码控制系统中,由每日产品编译系统自动触发,全自动运行。
    还有自己常规的Lab Pass也需要重装机器,模拟最终用户的使用形式。需要使用每日编译结果,规模大,测试数多,环境要求也复杂,在这时候我们就会把整个刚才我讲的测试者引进来,一天可能需要测试不同版本,或者不同语言版等。对测试结果汇报与问题要求很高,因为这时候所有测试必须百分之百的通过,可能前天有这么一个问题,今天这个问题重新出现,是不是就可以忽略了呢?如果这个报告结果工具不能干这个事,每天必须要重新做。由测试团队根据需要产生。测试团队的个人Private Pass,由测试个人根据需要产生,不一定需要重装机器,对测试结果汇报要求很高,与测试团队的关系近,在测试团队的源代码控制系统中。
    一个具体自动化测试系统分析。微软内部有很多套自动化测试系统,比如OASys,是Office用的系统,还有Maddog,Bruce等等。这些系统演化到最后,总体结构大同小异。如果大家自主开发一套新的自动化测试系统,我估计大概十年以后结果就是这样的。以OASys系统为例,有Web服务器,是前台的Web UI。SQL Server后台服务器,有控制程序,客户机程序,客户程序就是在机器上装一个小的程序,一些结果报告与分析的程序,有文件服务器,存放每天的构建的结果,每次结果的Log file等等,除此之外所有的测试都是在机器池中进行,一系列差不多一样的机器,在一个测试里随时调用某一群或者某一些,或者某一个机器进行使用。

   具体模块的功能:
   文件服务器是存放每日的结果,存放每一个Run的logfile。比如你需要安装什么东西,需要什么样的后台背景。
   SQL Server存放有关的Setup参数,存放所有与测试有关的参数,存放所有Client机器的情况,是什么样的机器,多少内存,系统时间是什么,现在在干什么等等 ,所有机器的情况都存在这里;还存放所有Run Pass的总体结果,运行数,通过率,运行机器名等……
    Web服务器是Web前台,等于说是一个Web配置。测试团队使用后台服务器的入口,好处就是只需要IE就可以运行,零安装,易集中更新。可以查询并修改所有存放在SQL Server中的参数,可以产生、查询并触发Lab Run,可以查询Lab Run进展状况,总体结果等。 还可以查询并调整客户机的状态,所安装的OS,程序等。
    机器池是几十台一样或比较接近的轻型机器,拥有操作系统或文件系统的镜像程序,可以进行自我更新。
    控制器程序,从SQL Server中读取工作数据,产生工作脚本,并把工作按客户机参数分配给客户机运行,当运行结束时,从Client得到结果并更新SQL Server,分为机房控制器与个人控制器等。Lab controller主要用于控制Lab里的Machine Pool,Private controller主要用于控制Office里的测试团队成员个人的机器。控制器程序应具有动态分配任务的功能,控制器程序应具有Load Balance的功能,控制器程序应能根据Lab Run的优先级与机器资源最优化的分配工作。比如说你有一个自动测试,一个自动化测试每次在Run的时候并不是只有一个测试,同时进行的可能有三到四个同时进行,有的Lab Run会进展的很慢,有些优先级很高。动态分配的功能是非常重要的,根据你的Lab Run的优先级,决定给你分配多少资源进行运行,这是非常重要的系统。还需要多少时间也是一个比较重要的功能,如果你有以前的数据,比如上次Lab Run以后,就知道每一个测试需要Run多少时间,把总体时间加起来,可以看到在今天的构建上还剩下多少时间。
    客户机程序。这个程序是一个非常小,非常轻型的程序,是运行在各个小的Client上面的,几乎是零安装,就是一个小程序,非常轻巧,因为他几乎不依靠于任何模块,可在裸机上运行,在微软里所有的模块都可能是需要测试的模块,如果客户机上运行的程序需要ADO这个东西,我们就需要测试这个ADO。可以用于完成控制器交给的任务并记录全过程,非常稳定,不会死机,并能截取大部分的异常情况。可以截屏,TimeOut,所有的系统都是在Lab自动运行的,全部是一些机器,没有人的。自动化运行系统很快,等于说一天24小时不停的进行。
    结果报告与分析程序,安装于测试团队成员的主机上。查询数据库并显示所要Run的状态,通过率,还需要时间等。进行简单的运行操控,如重新运行,指定主机运行等。最主要的是自动分析运行的结果文件,比较不同之处,列出改进与恶化的Test Case。刚才我讲的每天可能有成千成万的结果需要分析,成千成万的结果可能有很大一块早就已经分析过了,不想重新看这些结果,就要进行比较。各种各样的情况都能读出来,和存入的结果进行比较,得出新的需要分析的措施,你已经看过这些措施就不用管它了。这个程序分析完错误以后,可以输入失败错误的原因。提供结果文件的链接,Bug DataBase的链接,提供进一步分析结果的工具。记录Test Case失败的原因,并可直接输入与跟踪Bug号,当结果分析完毕,可记入为基准结果,以便于未来运行结果的比较。
    我们是怎样使用这一套系统的。首先一个测试经理得到一个测试的任务,比如说Windows 2000的任务,他可以把这个任务告诉一个人,这个人应该是测试团队的成员(LRF)担任,这个人干的活每次根据这些东西产生一些Run,要知道这个Run进入什么状态,是不是很成功等等,协助整个Run能够很平和的进行。这个人测试团队也不是有很多人愿意干这个活,大家就轮流干这个事情。LRF根据需求在Web UI用模板产生相应的Run,填入OS要求,语言要求,运行优先级,应完成时间等,把这些东西都输入进去。这个Run被控制器程序得到,得到以后就根据优先级,完成时间,可用机房机器数,合乎要求的机器数,测试总量等来分配任务。机房客户机得到任务,清理自己,安装要求的程序与模块,从文件服务器拷贝测试运行程序,执行测试并拷回结果。
    LRF通过Web UI跟踪Lab Run进展,检查有无重大问题,检查运行进展能否按时完成并作及时的调整,当Lab Run接近尾声,email测试团队验证各自结果。可以说测试者本身一般不会监测Lab Run进行。测试团队成员收到email打开我们刚才讲的结果报告与分析程序,最主要是新的错误,新的错误比如说是Bug,产生一个很小的Code,重现这个错误。
    测试程序的问题,测试程序本身Code上的问题,你要修改你的测试程序等等。如果是对于客户机安装的问题,一天整个系统每台不同的机器都是一个问题,比如今天XP统统都通过了,比较简单。最后测试经理对所有的结果汇总,也是在结果报告程序进行的,大家把成果分析完以后,测试经理自动产生一张总报表,会通过这个数据决定我们这个产品怎么办,不光是在最后汇总的时候用。
    做一个很快的回顾,对于一套测试自动化系统来说,对一个成熟的测试团队来说是非常重要的东西。如果一个测试团队如果没有一个完整的测试系统来说,没有办法进行一个测试。一个新开发的测试自动化系统,尽量通用化。我们的测试系统,什么都能做,可以看他系统设计的模块,并不是为了测试什么东西而设计,可以测试任何东西,所以Office这么大一个产品,里面任何东西都是在测试系统上测试,测试系统需求非常简单。对自动化测试本身来说,是非常简单的一个东西,什么都不知道,只知道产生一个结果,运行结果拷回去就完了。还有一些控制,控制我刚才讲的动态分配资源的问题。如果你要是机器数不够,这就是自动化测试控制,但是要测试什么东西,完全是由测试人员自己决定,所有自动的脚本都是自己编的,你就是存到文件服务器上就行了。每个测试自动化系统每一板块各有侧重,不必大而全。从测试自动化系统整个来说,一开始的前期投入可能大一些,大家可以看到,你要建立整套测试自动化系统,每个系统想方设法自动化、模块化,刚开始投入非常多,长远来说是很有利的。如果手工测试的话,后台那么多不同的应用程序,有各种不同XP的情况,不同语言的情况下,如果都用手工来做几乎不可以想象。如果有测试自动化系统,只要开发一次自动化以后,所有其他的机器都是自动运行的,不用再管他了。所以他对鼓舞整个团队的士气是非常重要的。一个测试者一天的工作,对测试结果来说非常简单,只要看一下每天的新的情况就完了,其他的事情都不用管。自动化测试对后期软件维护来说也是非常重要的。自动测试系统是什么都能测试,不管干什么都可以测试,针对你产品所有的测试自动化起来,如果只有一个版本可能是不行的,微软所有的产品Office已经有十二个版本了,这么多的版本程序来说,如果没有自动测试是难以想象的。如果有自动测试就可以同步测试使用,这样就可以达到事半功倍的效果,很快可以验证,可以避免重复劳动。自动测试定义软件系统,如果一个软件系统没有自动测试的话,后期维护,下一版本的发行都是难以想象的一件事情。

软件测试过程的持续完善

作者:qz
 1.引言
   随着软件技术的迅猛发展,软件的质量愈来愈受到广泛的重视。而测试又是保证软件质量的重要手段。根据IEEE/ANSI标准,软件测试的定义是:"使用为发现错误所选择的输入和状态的组合而执行代码的过程"。这就非常明确地提出了软件测试是以发现错误,检验是否满足需求为目标。软件测试在软件生命周期中占有非常突出的重要地位,是保证软件质量的重要手段。根据Boehm的统计,软件开发总成本中,用在测试上的开销要占40%到50%。软件测试的目的就是在软件投入生产性运行之前,尽可能多地发现软件中的错误,以提高软件的质量。现代的软件测试不仅仅是在软件开发完成以后来做测试工作,而是将测试渗入到软件开发的各个阶段,而且提高自动化软件测试手段,来提高测试效率。
  有些项目的主持人,认为以尽快的速度把测试之前的所有开发阶段完成(实际并没有完成),早日开始测试,以图达到快速和高质量(因为似乎有更长的时间可用于测试)。实际的效果将会是俗语所说的"欲速则不达"。从常识就可以知道,花开发时间去继续扩大发展前面阶段引入的错误,得出的只能是更大量的需要耗时修正的错误。 因此,正确分析与利用测试的结果,我们可以非常有效地进行软件过程改进。

2.完善测试过程策略

2.1. 双效合一,不断进步

  公司的管理层和质量控制小组通常进行软件过程的改善,并编写出了一系列的企业的标准与规范,经过一系列的评审、培训,然后让开发人员去执行。但是在执行过程中常常碰到阻力,多数是来自于开发人员,除了紧张的开发工作,他们往往会抱怨又多出许多其它工作,比如按照一定的规范的文档的撰写;制定的企业开发规范不符合企业的实际情况,标准太高,无法达到。这一种做法,费时费力不讨好,大家的意见都比较大,规范定的比较完美,而且在评审时还要大家表面上都要认可,制定规范的人花费了很大的精力,对规范的评审浪费了大家的很多的时间,执行时还难以贯彻下去。这种方式肯定收效甚微。这是一种效率比较低的做法。
  通常,还会有另外一种做法:降低要求,暂时抛弃各种标准与规范,采用一种简单易行的策略,即由质量控制小组找开发人员、项目经理让他们自我发现问题:你有什么缺点?你将如何改进?在开发人员、项目管理人员讲自己的改进措施后,让他们确保能做到。在这种办法中,不需要管理人员花费太多的精力进行标准的制定,改进的推动,这些工作都是由开发人员自己去做的,管理人员仅仅是起到了监督的作用,只要开发人员自己说到做到就可以了。但是,我们做了一个尝试,如果仅仅从开发人员的角度出发制定标准,每个人的习惯不同,开发人员往往倾向于按照平日自己的编程习惯制定符合自己需要的规范,这样做的随意性比较大,难以形成统一的、正规的文档体系结构。而且,开发人员往往利用这一点,给自己留有充分的弹性。往往自己制定的规范都有自己不同的解决办法,这样会造成编程风格的不统一。既然是规范,总得有一定的强制性,而如果单单从下而上,放权给开发人员,实施的过程中可能会发生更大的问题。
  综上所述,我们就采取了一个折中的办法,即,根据开发人员的要求,先拟订一份开发规范,然后提交给开发人员或者项目管理人员评审。允许他们提出自己的意见,如果意见合理,可以对规范实施修改。举例来说,假设公司原来的文档体系中本身有一套编程规范,但是在实际开发的时候,其中的某些规则不是很实用,所以,公司就根据每个项目组所使用的开发工具和语言的不同,制定不同的编程标准,而这些编程标准的修改意见,基本上来自于开发人员,但是是经过公司的管理人员和质量控制部审核过的。
  这种做法的好处就是可以主动提高公司全体员工的质量意识。对于高层管理人员而言,所有的规范都是经过他们审核批准的,他们起到监督作用;
对于开发人员而言,很多规则是他们提出的,他们会自觉遵守。这样双管齐下,双效合一,不仅会大大提高软件的质量,而且不用将发现错误的责任全部推给测试人员,而是提前预防错误、减少潜在危险的发生、减轻测试人员负担、培养开发人员良好的编程习惯。 2. 重视文档,需要技巧   软件文档也称文件,通常指的是一些记录的数据和数据媒体,它具有固定不变的形式,可被人和计算机阅读。它和计算机程序共同构成了能完成特定功能的计算机软件(有人把源程序也当作文档的一部分)。硬件产品和产品资料在整个生产过程中都是有形可见的,软件生产则有很大不同,文档本身就是软件产品。没有文档的软件,不称其为软件,更谈不上软件产品。软件文档的编制在软件开发工作中占有突出的地位和相当的工作量。高效率、高质量地开发、分发、管理和维护文档对于转让、变更、修正、扩充和使用文档,对于充分发挥软件产品地效益有着重要的意义。
  然而,在实际工作中,文档在编制和使用中存在着许多问题,有待于解决。软件开发人员中较普遍地存在着对编制文档不感兴趣的现象。从用户方面看,他们又常常抱怨:文档售价太高、文档不够完整、文档编写的不好、文档已经陈旧难于使用等等。
  众所周知,文档的编写对于开发人员来说是一个十分头疼的任务,本来开发周期就很紧,还要按照要求的格式撰写文档。所以,这样结果往往就是文档不全,或者文档过于简单致使测试人员看不懂。甚至于,有时候项目需求早就更新了,而文档的内容依然不变。
  换个角度想想看,如果文档不全,测试人员遇到不理解的地方肯定会去问相应的开发人员,那么开发人员肯定要花费时间做解释。如果测试人员和开发人员处在不同的工作地,这将造成十分的不便。
  在软件开发过程中,文档十分重要,书写文档工作量也是相当大的。但是,只要掌握住技巧,还是可以缓解这令人头疼的问题的。首先,要站在别人的角度上看待这个问题。自己是做开发当然必须十分清楚程序的流程及功能,但是其他人就不一定,包括测试人员。所以,不要排斥写文档,先要换个角度想问题。再次,阐述基本功能,要做到重点突出。就是说,用简单的语言把功能简要介绍。对于其中的重点部分,要突出,要详细。不是说语言上要十分详细,而是理解的角度要详细。为了让测试人员快速理解模块的功能,最好的办法就是:功能流程图、数据流程图和例子。尤其是对于那些有相当强逻辑的程序而言,数据流程图和例子是非常好的方法,它不仅可以帮助指明数据的流向,还可以帮助测试人员理解测试用例的类型,以及结果形式。制作简明扼要的流程图和例子对开发人员而言是一项理清思路、省时省力的工作。而对于测试人员而言则是一份理解程序逻辑和功能的重要文档。在开发过程的后期,可以继续细化和完善文档。

2.2. 结队编程,提前测试

  为了提高软件的质量,公司可以尝试实行先结队编程,这其中也贯穿着质量意识。因为组成队的两个开发人员轮流编程、轮流写文档、互相监督、互相测试。这样不仅可以有精力把文档写好写全,而且可以提前单元测试,互相监督对方养成好的编程习惯。最终提高工作效率。 结队编程后,单元模块先由项目组配备的测试人员首先进行测试,然后质量控制部的人员按照项目计划检查项目是否按照预定计划正常进行,相关文档是否撰写,并进行集成测试。

2.3. 善于总结,提高效率

  总结是一种非常好的学习方法,它可以节省精力、节约时间达到事半功倍的效果。在项目的开发过程中,可以将碰到的重要的技术方面的问题要及时记录并将解决方案也记录下来,以便于其他相关人员的参考。同样,在测试的过程中,测试人员应该及时总结发现的错误并归类,标明经常容易出错的地方,将意见提交项目经理,审核后,制定出一份统一标准并提供给开发人员,这样就可以提前避免错误、避免重复错误和重复测试,提高测试效率。不仅如此,项目结束后的各项总结报告将是项目的后期维护或二次开发的宝贵参考资料。

3.结论

        软件开发作为一种复杂的智力密集型的活动,同一般产品的设计和生产过程有相当大的差别,人的因素占的比例很大,控制也更为复杂。例如软件的正确性无法证明、测试也很困难,如果希望通过最终的测试确保产品的质量是完全做不到的;生命周期的各个阶段的转化无法确保百分之百的正确和完整,等等。实践证明,如果不从本公司的实际情况出发,盲目地套用一些好高骛远的开发体系或者质量体系文件是行不通的,所建立的体系对提高管理水平非但不能起到多大的促进作用,而且可能会对正常的开发活动起阻碍作用,引起开发人员的反感。这样建立的体系或者难于维持下去,或者要花费宝贵的资源去维持一套无用的体系。所以,建议根据公司的实际量身定做,建立起一套符合本公司情况的切实可行的标准和规范,真正的改善软件过程,加强测试,提高软件质量。

软件测试组织与方法

作者:范智华 来源:天极
   
    随着计算机硬件成本的不断下降,软件在整个计算机系统的成本中占有越来越高的比例,如何提高软件质量是整个计算机软件行业的重大课题。软件测试作为软件开发的一个重要环节,日益受到人们的重视。为了尽可能多地找出程序中的错误,生产出高质量的软件产品,加强对测试工作的组织和管理就显得尤为重要。

1. 软件生存周期

    一个软件从开始计划起,到废弃不用止,称为软件生存周期。一般来说,软件生存周包括计划、开发、运行三个时期,每一时期又可分为若干更小的阶段。计划时期的主要任务是分析用户要求,分析新系统的主要目标以及开发该系统的可行性。开发时期要完成设计和实现两大任务具体。具体分为需求分析、概要设计、详细设计、编码、测试。其中编码和测试是软件开发期的最后两个阶段。运行时期是软件生存周期的最后一个时期,软件人员在这一时期的工作,主要是做好软件维护。
  统计表明,开发较大规模的软件,有40%以上的精力是耗费在测试上的,即使富有经验的程序员,也难免在编码中发生错误,何况,有写错误在设计甚至分析阶段早已埋下祸根,无论是早期潜伏下来的错误或编码中新引入的错误,若不及时排除,轻者降低软件的可靠性,重者导致整个系统的失败。为防患于未然,强调软件测试的重要性是必要的。

2. 测试的过程与方法

2.1、 测试的目的

    在G.J.Myers的经典著作《软件测试技巧》中,给出了测试的定义: "程序测试是为了发现错误而执行程序的过程"。测试的目的是发现程序中的错误,是为了证明程序有错,而不是证明程序无错。在软件开发过程中,分析、设计与编码等工作都是建设性的,惟独测试是带有"破坏性",测试可视为分析、设计和编码3个阶段的"最终复审",在软件质量保证中具有重要地位。为了确保软件的质量,较理想的做法应该是对软件的开发过程,按软件工程各阶段形成的结果,分别进行严格的审查。

2.2、测试的过程

     当设计工作完成以后,就应该着手测试的准备工作了,一般来讲,由一位对整个系统设计熟悉的设计人员编写测试大纲,明确测试的内容和测试通过的准则,设计完整合理的测试用例,以便系统实现后进行全面测试。
  在实现组将所开发的程序经验证后,提交测试组,由测试负责人组织测试,测试一般可按下列方式组织:
  (1)首先,测试人员要仔细阅读有关资料,包括规格说明、设计文档、使用说明书及在设计过程中形成的测试大纲、测试内容及测试的通过准则,全面熟悉系统,编写测试计划,设计测试用例,作好测试前的准备工作。
  (2)为了保证测试的质量,将测试过程分成几个阶段,即:代码审查、单元测试、集成测试和验收测试。
  (3)代码会审:
  代码会审是由一组人通过阅读、讨论和争议对程序进行静态分析的过程。会审小组由组长,2~3名程序设计和测试人员及程序员组成。会审小组在充分阅读待审程序文本、控制流程图及有关要求、规范等文件基础上,召开代码会审会,程序员逐句讲解程序的逻辑,并展开热烈的讨论甚至争议,以揭示错误的关键所在。实践表明,程序员在讲解过程中能发现许多自己原来没有发现的错误,而讨论和争议则进一步促使了问题的暴露。例如,对某个局部性小问题修改方法的讨论,可能发现与之有牵连的甚至能涉及到模块的功说明、模块间接口和系统总结构的大问题,导致对需求定义的重定义、重设计验证,大大改善了软件的质量。
  (4)单元测试:
  单元测试集中在检查软件设计的最小单位-模块上,通过测试发现实现该模块的实际功能与定义该模块的功能说明不符合的情况,以及编码的错误。由于模块规模小、功能单一、逻辑简单,测试人员有可能通过模块说明书和源程序,清楚地了解该模块的I/O条件和模块的逻辑结构,采用结构测试(白盒法)的用例,尽可能达到彻底测试,然后辅之以功能测试(黑盒法)的用例,使之对任何合理和不合理的输入都能鉴别和响应。高可靠性的模块是组成可靠系统的坚实基础。
  (5)集成测试:
  集成测试是将模块按照设计要求组装起来同时进行测试,主要目标是发现与接口有关的问题。如数据穿过接口时可能丢失;一个模块与另一个模块可能有由于疏忽的问题而造成有害影响;把子功能组合起来可能不产生预期的主功能;个别看起来是可以接受的误差可能积累到不能接受的程度;全程数据结构可能有错误等。
  (6)验收测试:
  验收测试的目的是向未来的用户表明系统能够像预定要求那样工作。经集成测试后,已经按照设计把所有的模块组装成一个完整的软件系统,接口错误也已经基本排除了,接着就应该进一步验证软件的有效性,这就是验收测试的任务,即软件的功能和性能如同用户所合理期待的那样。
  经过上述的测试过程对软件进行测试后,软件基本满足开发的要求,测试宣告结束,经验收后,将软件提交用户。

2.3.测试方法分析

  集成测试及其后的测试阶段,一般采用黑盒方法。
  (1)用边值分析法和(或)等价分类法提出基本的测试用例;
  (2)用猜测法补充新的测试用例;
  (3)如果在程序的功能说明中含有输入条件的组合,宜在一开始就用因果图法,然后再按以上(1)、(2)两步进行。
  单元测试的设计策略稍有不同。因为在为模块设计程序用例时,可以直接参考模块的源程序。所以单元测试的策略,总是把白盒法和黑盒法结合运用。具体做法有两种:
  a、先仿照上述步骤用黑盒法提出一组基本的测试用例,然后用白盒法作验证。如果发现用黑盒法产生的测试用例未能满足所需的覆盖标准,就用白盒法增补新的测试用例来满足它们。覆盖的标准应该根据模块的具体情况确定。对可靠性要求较高的模块,通常要满足条件组合覆盖或路径覆盖标准。
  b、先用白盒法分析模块的逻辑结构,提出一批测试用例,然后根据模块的功能用黑盒法进行补充。

3. 测试人员组织

 人是测试工作中最有价值也是最重要的资源,没有一个合格的、积极的测试小组,测试就不可能实现。为高质高效地完成测试任务,好的测试工程师应具有如下能力:

3.1、沟通能力

    一名理想的测试者必须能够同测试涉及到的所有人进行沟通,具有与技术(开发者)和非技术人员(客户,管理人员)的交流能力。既要可以和用户谈得来,又能同开发人员说得上话,不幸的是这两类人没有共同语言。和用户谈话的重点必须放在系统可以正确地处理什么和不可以处理什么上。而和开发者谈相同的信息时,就必须将这些活重新组织以另一种方式表达出来,测试小组的成员必须能够同等地同用户和开发者沟通。

3.2、技术能力

    就总体言,开发人员对那些不懂技术的人持一种轻视的态度。一旦测试小组的某个成员作出了一个错误的断定,那么他们的可信度就会立刻被传扬了出去。一个测试者必须既明白被测软件系统的概念又要会使用工程中的那些工具。要做到这一点需要有几年以上的编程经验,前期的开发经验可以帮助对软件开发过程有较深入的理解,从开发人员的角度正确的评价测试者,简化自动测试工具编程的学习曲线。

3.3、自信心

    开发者指责测试者出了错是常有的事,测试者必须对自己的观点有足够的自信心。如果容许别人对自己指东指西,就不能完成什么更多的事情了。

3.4、外交能力

    当你告诉某人他出了错时,就必须使用一些外交方法。机智老练和外交手法有助于维护与开发人员的协作关系,测试者在告诉开发者他的软件有错误时,也同样需要一定的外交手腕。如果采取的方法过于强硬,对测试者来说,在以后和开发部门的合作方面就相当于"赢了战争却输了战役"。

3.5、幽默感

    在遇到狡辩的情况下,一个幽默的批评将是很有帮助的。

3.6、很强的记忆力

 一个理想的测试者应该有能力将以前曾经遇到过的类似的错误从记忆深处挖掘出来,这一能力在测试过程中的价值是无法衡量的。因为许多新出现的问题和我们已经发现的问题相差无几。

3.7、怀疑精神

    可以预料,开发者会尽他们最大的努力将所有的错误解释过去。测式者必须听每个人的说明,但他必须保持怀疑直到他自己看过以后。

3.8、自我督促

    干测试工作很容易使你变得懒散。只有那些具有自我督促能力的人才能够使自己每天正常地工作。

3.9、洞察力

    一个好的测试工程师具有"测试是为了破坏"的观点,捕获用户观点的能力,强烈的质量追求,对细节的关注能力。应用的高风险区的判断能力以便将有限的测试针对重点环节。
  总之,测试是软件生存周期中的一个关键的阶段,也是保证软件质量的重要活动之一。无论怎样强调软件测试的重要性和它对软件可靠性的影响都不过分,面对软件开发规模的增大、复杂程度的增加,更应高度重视软件测试工作的组织与管理,以提到软件质量。