本文转载,原文请点击链接
黑盒测试与白盒测试
在第一弹中我们介绍过,软件的测试包含单元测试、集成测试、系统测试和回归测试四个阶段。那么,这里我们先来看下各个阶段都使用怎样的测试方法。
软件测试,从测试方法上来区分可以分为黑盒测试、白盒测试和灰盒测试。
这边讲下集成测试和系统测试的区别
集成测试在系统测试之前,单元测试完成之后系统集成的时候进行测试。集成测试主要是针对程序内部结构进行测试,特别是对程序之间的接口进行测试。集成测试对测试人员的编写脚本能力要求比较高。测试方法一般选用黑盒测试和白盒测试相结合。
系统测试最主要的就是功能测试,测试软件《需求规格说明书》中提到的功能是否有遗漏,是否正确的实现。做系统测试要严格按照《需求规格说明书》,以它为标准。测试方法一般都使用--黑盒测试..
黑盒测试
黑盒测试,也称为功能测试。测试者不了解程序的内部情况,不需具备应用程序的代码、内部结构和编程语言的专门知识。只知道程序的输入、输出和系统的功能,这是从用户的角度针对软件界面、功能及外部结构进行测试,而不考虑程序内部逻辑结构。测试案例是依应用系统应该做的功能,照规范、规格或要求等设计。测试者选择有效输入和无效输入来验证是否正确的输出。
此测试方法可适合大部分的软件测试,如集成测试以及系统测试。
黑盒测试主要是为了发现以下几类错误:
是否有不正确或遗漏的功能?
在接口上,输入是否能正确的接受?能否输出正确的结果?
是否有数据结构错误或外部信息(例如数据文件)访问错误?
性能上是否能够满足要求?
是否有初始化或终止性错误?
白盒测试
白盒测试又称透明盒测试、结构测试等。测试应用程序的内部结构或运作,而不是测试应用程序的功能(即黑盒测试)。在白盒测试时,以编程语言的角度来设计测试案例。测试者输入数据验证数据流在程序中的流动路径,并确定适当的输出,类似测试电路中的节点。测试者了解待测试程序的内部结构、算法等信息,这是从程序设计者的角度对程序进行的测试。
白盒测试可以应用于单元测试、集成测试和系统的软件测试流程。
白盒测试主要是想对程序模块进行如下检查:
对程序模块的所有独立的执行路径至少测试一遍。
对所有的逻辑判定,取“真”与取“假”的两种情况都能至少测一遍。
在循环的边界和运行的界限内执行循环体。
测试内部数据结构的有效性,等等。
灰盒测试
灰盒测试,是介于白盒测试与黑盒测试之间的一种测试,灰盒测试多用于集成测试阶段,不仅关注输出、输入的正确性,同时也关注程序内部的情况。灰盒测试不像白盒那样详细、完整,但又比黑盒测试更关注程序的内部逻辑,常常是通过一些表征性的现象、事件、标志来判断内部的运行状态。
软件测试词汇表
- 单元测试(unit test):
可测试代码的最小的一部分。通常是一个单一的方法,不会使用其它方法或者类。非常快!上千个单元测试能够在10秒以内跑完!单元测试永远不会使用:
- 数据库
- 一个app服务器(或者任何类型的服务器)
- 文件/网络 I/O或者文件系统
- 另外的应用
- 控制台(System.out,system.err等等)
- 日志
- 大多数其他类(但不包括DTO‘s,String,Integer,mock和一些其他的类)
单元测试几乎总是回归测试套件(regression suite)的一部分。
- 回归测试套件(Regression Suite):
能够立刻被运行的测试用例的集合。一个例子就是放在一个特定文件夹中的能够被Junit运行的所有测试用例。一个开发人员能够在一天中把一个单元测试回归套件运行20次或者他们可能一个月跑两次功能测试回归套件。
- 功能测试(Functional Test):
比一个单元要大,比一个完整的组件测试要小。通常为工作在一起的的几个方法/函数/类。上百的测试用例允许运行几个小时。大部分功能测试是功能测试回归套件的一部分。通常由Junit来运行。
- 集成测试(Integration Test):
测试两个或者更多的组件一起工作的情况。有时候是回归套件的一部分。
- 组件测试(Component Test):
运行一个组件。经常由QA,经理,XP客户等等来执行。这种类别的测试不是回归套件的一部分,它不由Junit来执行。
- 组件验收测试(Component Acceptance Test C.A.T.):
作为正常流程的一部分,它是在众多人面前运行的一个组件测试。由大家共同决定这个组件是不是满足需求标准。
- 系统测试(system Test):
所有的组件在一起运行。
- 系统验收测试(System Acceptance Test S.A.T.):
作为正常流程的一部分,它是在众多人面前运行的一个系统测试,由大家来共同决定这个系统是不是满足需求标准。
- 压力测试(Stress Tests):
另外一个程序加载一个组件,一些组件或者整个系统。我曾经看到过把一些小的压力测试放到回归功能测试中来进行——这是测试并发代码的一个很聪明的做法。
- Mock:
在单元测试或者功能测试中使用的一些代码,通过使用这些代码来确保你要测试的代码不会去使用其它的产品代码(production code)。一个mock类覆盖了一个产品类中的所有public方法,它们用来插入到尝试使用产品类的地方。有时候一个mock类用来实现一个接口,它替换了用来实现同样接口的产品代码。
- Shunt:
有点像继承(extends)产品代码的mock类,只是它的意图不是覆盖所有的方法,而只是覆盖足够的代码,所以你能够测试一些产品方法,同时mock剩余的产品方法。如果你想测试一个可能会使用I/O的类它会变得尤为有用,你的shunt能够重写I/O方法同时来测试非I/O方法。
对代码做白盒测试
上面介绍了软件测试中的黑盒、白盒和灰盒测试。白盒测试被广泛的使用在单元测试阶段。
这里我们先来分析下,我们要进行单元测试,需要做哪些事情?因为单元测试的主要手段是白盒测试,白盒测试的测试方法是:测试者输入数据验证数据流在程序中的流动路径,并确定适当的输出。那么整个测试流程大概需要包含以下几个步骤:
- 初始化测试环境、准备测试数据。
- 调用需要被测试的单元。
- 收集结果,并与期望值比较。
- 测试数据清理。
以上四个步骤在每个单元在被测试的时候都需要被执行。举个例子,我们有一个除法运算的方法,我们要对他做单元测试。
public class Calculator{ public float divide(float divisor,float dividend){ return divisor/dividend; } }
我们要在程序中验证上面这个方法的正确性,一般会写以下代码来测试他:
public class CalculatorTest{ public static void main(String [] args){ Calculator calculator = new Calculator(); float result = calculator. divide(10.0,2.0); if(result == 5.0){ System.out.println("divide test ok"); }else{ System.out.println("divide test failed"); } } }
这只是对该方法测试的第一个测试,如果我想测试这个方法在被除数是0的情况下会怎么样,那么我就要再写一个CalculatorTest2,然后重写写一个main方法,再重新定义一个Calculator对象,然后在调用divide方法的时候把第二个参数的值传为0。
其实上面的测试是存在很大问题的,因为在内存中并无法精确的存储浮点数,当我们把两个浮点数相除的时候结果并不一定可以精确的存储下来,而我们的逾期结果却是一个精确值,这样的比较可能会不相等的。但是这样的情况需要多个case才有可能被发现。
所以,我们在测试一个类中的一个方法的时候,可能要定义大量的类,然后需要分别执行,并且通过看控制台的输出才能确认结果。
这里,请先记住这些问题,因为,接下来我们要介绍的测试框架会帮我们解决这些问题的。
单元测试框架
通常,在没有特定框架支持下,我们在对一个方法进行单元测试的时候,无外乎是使用分支判断、异常处理、流程控制等来控制代码的执行,通过程序输出来表示方法的执行成功和失败。这样存在的最大问题就是我们每执行完一个单测之后,都要去控制台看输出才知道单元测试有没有成功,这明显是不合理的,因为单元测试是需要自动化执行的,程序没办法帮我们检查输出是否正确的。
单元测试框架就解决了这个问题,一旦使用了框架,加入单元测试相对来说会简单许多。通常,Java中常用的单元测试框架一般包含三个功能:测试工具、测试套件、测试运行器。
- 测试工具
- 测试工具是一整套固定的工具用于基线测试。测试工具的目的是为了确保测试能够在共享且固定的环境中运行,因此保证测试结果的可重复性。一般负责初始化测试环境、准备测试数据和测试数据清理。
- 测试套件
- 测试套件意味捆绑几个测试案例并且同时运行。
- 测试运行器
- 用于执行测试案例。一般负责调用需要被测试的单元、收集结果、并与期望值比较。
除了以上这些功能之外,针对不同的功能,一般还会提供很多API和语法支持。
下一弹会重点介绍如何使用JUnit进行单元测试。
参考资料
来源:https://www.cnblogs.com/54chensongxia/p/12410880.html