基于约束的服务化软件测试系统
2019-06-11李昌建钱巨程浩周辉
李昌建 钱巨 程浩 周辉
摘要:面向服务的软件体系结构近年来不仅在民用领域得到广泛应用,也越来越多地应用于军用装备软件系统研制。服务化软件的测试技术得到了越来越多的关注。传统的服务化软件测试工具大多关注于测试流程的自动化,在测试用例的自动生成等方面,还远不够成熟。现有测试技术和工具尤其难以表达真实应用中的业务逻辑规则,给生成高质量的测试带来许多困难。鉴于此,研发了一款针对服务化系统的软件测试原型工具。该工具运用一阶逻辑公式表达业务逻辑约束,基于23 SMT约束求解器生成测试用例、进行故障注入等,使得测试数据的生成更契合待测软件业务特征,为服务化软件的测试实践提供了更有力支持。
关键词:Web服务;软件测试;测试用例生成;故障注入;SMT
中图分类号:TP311
文献标识码:A
面向服务的软件体系结构近年来不仅在民用领域得到广泛应用,也越来越多地应用于军用装备软件系统研制。包括我国在内,许多国家的C4ISR军用信息系统中均已开始应用Web服务技术[1]。Web服务技术的广泛应用对服务化软件系统的可靠性、安全性提出了更高要求。作为保障可靠性与安全性的一种重要手段,服务化软件的测试技术也得到了越来越多的关注。国外的SoapUI[2]、ParasoftSOAtest[3]、SoapSnoar[4]等工具,已为Web服务系统的测试提供了许多支持。研究者们也广泛探讨了各类Web服务测试技术[5][6]。然而,现有的服务化软件测试工具大多关注于测试流程的自动化,重在运用工具来完成消息报文的发送和收集等。在测试用例的自动生成等方面,还远不够成熟。现有测试技术和工具尤其难以表达真实应用中的业务逻辑规则,给生成高质量的测试带来许多困难。比如,在服务单元的测试用例生成方面,大多数工具仅能根据整数、浮点数等接口数据类型,使用随机、边界值等方式生成测试数据。对于接口数据存在复杂业务逻辑相关约束条件的情况处理能力较为有限,生成的测试数据不贴近待测应用的业务特性,有效性较差。德国的Heckel等[7]、北京大学的姜瑛等[8]、清华大学的白晓颖等[9]、西北工业大学侯俊等[10]研究了数据存在约束条件情况下的测试用例生成问题。他们用区间限制、OWL-S等机制表达接口数据上存在的约束。其中,尽管OWL-S等机制具有较强的约束表达能力,但这些工作在根据约束生成测试用例时,大多只能处理约束施加在单一输入因素上的情况,对于形如a
随着SMT求解[11]等技术的发展,约束系统在表达能力和求解能力等方面得到了长足进步,也涌现了23[12]等一批成熟的约束求解工具,为构建新型的基于约束求解的测试工具提供了契机。据此,本文提出了一个基于约束的服务化软件测试原型工具,该工具使用一阶逻辑作为约束的主要表达方式,利用23 SMT约束求解器来支持复杂约束条件下的测试用例生成。除了将约束求解技术应用于Web服务单元级的测试用例生成,工具还将约束求解技术应用于服务调用序列的生成、基于符号执行的组合服务测试数据生成、面向业务逻辑的故障注入等方面,拓宽了约束系统在服务化软件测试领域的应用范围。在测试方法支持的数据类型及类型上的运算方面,借助23工具强大的约束求解能力,工具不仅能够支持一般整数类型上的线性运算,还能夠对浮点数上的测试数据。生成提供一定程度的支持,甚至支持按位运算等约束系统中可能出现的复杂运算公式。通过对字符串进行整数编码,以及应用基于正则表达式的字符串生成等技术,拓广了测试功能能够支持的Web服务类型范围。
1 系统结构
Web服务测试原型工具基本界面如图1所示。该工具支持Web服务描述的静态检测、服务单元测试、服务调用序列测试、组合服务测试、服务故障注入测试、Web服务性能测试等核心功能,如图2所示。其中,工具通过独立的约束系统管理模块,来维护待测项目中的各种业务逻约束。这些约束依赖于待测应用的功能特性,而非测试过程中的某一具体活动,可广泛应用在服务单元的测试用例生成、服务调用序列生成、组合服务测试用例生成、服务故障注入等多个方面。
为保证灵活性,测试工具采用了如图3所示的物理结构。整个系统由测试用例设计器TestDe-signer、测试任务执行器ServiceExecutor、服务部署容器SvcHost、以及代理转发网关RedirectProxy四大基本模块构成。
测试用例设计器TestDesigner负责测试用例的设计、测试结果的收集等任务,提供一个用户界面,以便于用户编辑和查阅测试用例及其执行信息。测试任务执行器ServiceExecutor从测试用例设计器接收测试任务,根据任务要求展开实际测试动作,该模块也可脱离用户界面,通过脚本驱动。服务部署容器SvcHost用于发布待测服务和安装、控制虚拟服务。代理转发网关RedirectProxy用于监控不同服务之间的消息流。可在代理网关上设定故障注入或性能控制要求,以控制目标服务的功能和性能表现。
2 约束系统管理
原型工具采用集中管理方式维护待测应用中的业务逻辑约束。图4展示了工具中的约束管理界面。系统支持23约束求解工具能够处理的大部分一阶逻辑约束公式。为便于结合Web服务的特点来表达约束关系,测试工具定义了自己的约束表达语言,该语言将被翻译为23约束求解工具接受的约束语言以进行约束求解,所得的约束满足或不满足解将被翻译映射回Web服务上的相关数据,以进行测试。
2.1 约束变量
约束公式建立的基础是约束变量,系统支持两种类型的约束变量。
1)值约束变量。其表达形式为
value( svc/operation/message_path),
其中value是变量类型名,用以区分其它类型的约束变量。svc是服务标识,用以区分不同的服务,可通过宏定义方式预先定义出svc名称的具体含义。operation是Web服务的操作的名称,mes-sage_path是由操作到基本元素参数的路径。例如“svc=http: //test.com/axis2/services/Add”表达add服务的服务地址,可通过svc值找到服务。“value( svc/add/a)”表达svc服务中的add操作的a参数的取值。
2)时间约束变量。其形式为
startTime( svc/operation)
其中startTime是约束变量的类型名称,整个约束变量表达了某一服务某一操作在服务调用过程中的启动时间。
2.2 约束公式
工具中的约束公式本质上是23求解器支持的一阶逻辑公式,可以建立在单个服务操作的不同参数之间。包括输入参数之间,用以表达输入数据上的限制;也包括输入和输出参数之间,用以描述一个服务操作的输出和输入之间可能存在的某种联系。约束公式还可以建立在不同服务之间,主要用于描述服务调用在时序上应该存在的关系。典型的约束公式示例如下。
1)值约束。形如
value( svc/add/a)< value( svc/add/b),
表达svc服务中add操作的a参数取值应小于b参数取值。
2)时序约束。形如
startTime( svc/add) 表达svc服务add操作的调用应该在multiple操作之前。 约束用AND、OR、NOT关系构成的树进行组织。树的叶节点是基本约束,每个约束含有一条约束公式。基本约束通过AND、OR、NOT关系构成更复杂的约束系统。每个约束节点可以命名,以直观表达约束的含义。例如 value (svc/add/a)>0 and value (svc/add/a) 表达svc服务中add操作包含两个基本约束,并通过AND关系组合成一个复杂约束。3 基于约束的服务单元测试用例生成 原型工具支持基于约束来生成有效和无效测试数据。针对每个待测服务操作,可以生成满足约束的有效测试数据或者不满足约束的无效測试数据。测试用例的具体生成流程如图5所示。首先从待测项目的整个约束树中提取目前所关注的服务操作相关的约束,例如“value( svc/add/a)+1 第二步,建立从服务操作输入数据到各个约束变量之间的关联,约束变量的求解结果即这些参数将要设定的取值。然后,利用23求解引擎进行约束求解,目前系统支持线性不等式约束、布尔约束、按位运算约束、字符串枚举类型上的判定等约束类型。下一步,根据求解所获得的约束变量取值导出服务操作的参数取值设定。最后,根据参数取值构造服务操作测试时所需的完整SOAP数据包,以发起服务调用。 例如,对于Add服务规定add操作规定参数值α小于参数值b,生成满足约束的测试数据的操作如下。首先提取约束到约束配置界面,给出约束标识svc的值“svc=http://test.com/axis2/services/Add”及约束表达式的具体形式其次,“value( svc/add/a) 测试用例生成中,基于约束生成无效测试数据的过程与生成有效测试数据的过程非常接近。主要差别在于获得所有约束后,需要对约束取反,从而求解获得违反约束的不合理取值。 在Web服务中,经常需要使用字符串类型,字符串常以枚举常量形式出现,以作为状态标识等。为支持字符串类型上的测试生成,我们用整数对所有出现的字符串常量进行编码,如此,字符串在某一枚举集中取值、字符串相等、字符串不等等问题,可以转化为整数上的判等问题,同样可采用23工具进行约束求解。获得相应的解后,我们将整数编码重新映射回字符串,可以获得满足或不满足约束要求的字符串。一些字符上常存在正则表达式表示的模式限制,比如要求密码字符串的模式为[0-9][0—9][0—9],表示密码是三个数字构成的串。对此,原型工具使用Xeger程序库[13],借助基于正则表达式的字符串生成技术来生成相应的满足或不满足约束的串。4 基于约束的服务调用序列测试生成 服务调用序列可用于检测服务内部是否正确实现了无状态特性,不会因历史上的其它调用而影响后续的服务执行,也可检测数据是否能够在相关服务操作间有效流转,对于服务系统整体的质量保证具有重要意义。 在服务调用序列测试中,我们首先需要根据服务操作间输入输出参数的匹配情况、多维组合覆盖要求等,生成用于测试的候选服务操作调用序列。然而,并非上述每一序列对于实际测试均有意义。一个服务化应用的功能特性可能决定在用户的使用过程中,A服务操作的调用永远发生在B服务操作之前,这时测试A操作发生于B操作之后的服务调用序列显然意义不大,需要将此类序列进行排除。另一类情况下,服务实现人员可能认为用户一定先调用A操作,然后再调用B操作,而实际情况中,用户可能按相反的顺序使用。这时,为测试服务系统的健壮性,反而需要测试B先A后的情况。为支持上述测试,本测试工具支持对服务操作间的合理调用时序进行约束建模,然后根据时序约束的满足与不满足性来生成用于测试的服务调用序列。
服务调用序列的生成过程以满足输入输出参数的类型匹配要求为首要出发点,首先根据上述要求生成一批前后服务调用间输入输出能够全部或部分衔接的候选序列。然后,根据约束满足情况对这批候选序列进行过滤,获得有效或无效测试序列。在此基础上,再根据组合要求进行进一步测试用例选择。
在检验一个候选服务调用序列是否满足业务逻辑限定的时序约束时,首先从待测项目的约束系统中,找出相关服务操作对应的时序约束关系,即一组startTime约束变量上的不等式。例如,如下约束:
startTime( svc/add) 限定了svc服务中的add操作一定发生在其sub操作之前。 然后,将待检测的候选序列所蕴含的操作间先后关系也转换为startTime大小关系加入到约束表中。例如,对于一个操作序列,其蕴含的时序约束可以表达为:startTime(a) 最后,取用户定义的业务逻辑约束和当前候选序列中所蕴含的先后约束关系联立为不等式组,采用23求解器进行约束求解。如果不等式组有解,表明能够找到各个服务操作的startTime()变量取值,使得无论是用户的业务逻辑要求,还是当前序列所要求的顺序都能够得到满足,当前生成的这个操作序列是合理的;否则表明当前操作序列不合理,序列为无效服务操作调用序列,对应无效测试用例。 例如,对于Calculate服务,其中的蕴含的时序约束表达为:“startTime(add) 5 基于约束的故障注入 本服务化软件测试原型工具还支持基于约束的故障注入。故障注入过程首选选择一批测试用例作为注入基础,然后选择一批注入点来实施注入。故障注入点以服务操作进行标识。这些服务操作可以是基础测试用例中直接调用的服务操作,也可以是基础测试用例所调用的服务操作内部所间接调用的其它服务操作。 本测试系统中,所有的服务间消息传递都经过RedirectProxy代理模块,因此,在该代理中进行监控,可以比较方便地识别各个故障注入点。通过在代理过程中,将原先的正常输入数据替换为异常数据,可以注入错误,检测整个服务化系统对于异常的容错情况。 原型系统支持面向消息结构的注入、面向通信的注入、面向业务逻辑的注入三种注入方式。面向消息结构的注入主要注入不匹配预定消息格式的SOAP报文,如增加无效参数节点、删除有效参数节点、参数节点乱序等;面向通信的注入主要注入网络传输故障,如消息重复、消息丢失、消息乱序的等;而面向业务逻辑的注入主要注入结构合法,但数据内容不满足业务逻辑约束的异常数据。 对于面向业务逻辑的故障注入,如果某add服务正常情况下相关业务逻辑要求其a参数取值小于b参数,即: value( svc/add/a)< value( svc/add/b). 那么,在故障注入中,我们会对正常的输人参数进行篡改,使得α的值大于等于b。如此,可以注入一个格式正常,但数据内容通常不会出现的异常情况。例如,对于以上约束,我们将通过取反,获得其否定形式: not value( svc/add/a)< value( svc/add/b) 通过利用SMT求解器求解该约束条件,可以生成一个违反业务逻辑的故障数据{a=98,b=98)。该故障数据可以模拟由于软硬件错误造成程序逻辑异常的情况,将更接近真实场景中可能发生的故障。测试用例生成后,故障注入选项选择“违反取值约束”选项。 故障注入测试实施后,系统将报告测试执行结果,同时展示生成的异常报文,以便于用户了解容错情况。如图8所示,Add服务故障注入前的数据是{a=98,b=99),故障注入后的数据为{a=869,y=99},测试执行结果数据为{result=968}。 6 结论 测试工具的主要创新点是将约束表达与求解技术广泛应用在服务化软件的测试用例生成、故障注入等多个领域,较之已有工具,具有更强的测试分析设计能力,能够支持用户进行更高效的测试。在约束的处理方面,使用了前沿的SMT约束求解技术,能够表达和处理丰富的约束类型,能够处理不同输入输出因素之间的关联性约束,使得更多的业务逻辑限制能够得到有效表达和处理,从而可以改进测试数据的生成质量。 對服务的约束处理目前支持的约束有值约束和时序约束可满足多数场景下的测试需求,对于非线性约束等其他约束值得在未来进一步研究。同时,对于约束中字符串的处理,当前操作使用整数编码的形式进行处理,未来可以考虑使用23-str进行处理。 参考文献: [1] LAU Y T.“Service -oriented architecture and the C4ISR frame-work”[J]. The Journal of Defense Software Engineering,2004(9):11-14 [2]KANKANAMGE C. Web services testing with soapUI[M].Birm-ingham: Packt Publishing Ltd, 2012. [3]Parasoft SOAtest [EB/OL](2016-09-27) [2018-03-14]. https://www.parasoft. com/product/soatest
[4]SOAPSonar [EB/OL] (2018 -02-13) [2018 -03 -14]. http://www.crosschecknet.com/products/soapsonar.php/
[5]BOZKURT M.HARMAN M.HASSOUN Y.Testing and verifica-tion in service-oriented architecture:a survey[J].Software Test-ing, Verification and Reliability, 2013: 261-313
[6] QIU D, LI B X.JI S H,et al.Regression testing of web service:asystematic mapping study[J].ACM Computing Surveys, 2014, 47(1):21-46.
[7] HECKEL R,LOHMANN M."Towards contract-based testing ofweb services,”[J].Electronic Notes in Theoretical Computer Sci-ence, 2005, 116(19): 145-156.
[8]姜瑛,辛国茂,单锦辉,等.一种Web服务的测试数据自动生成方法[J]计算机学报.2005 (4):568-577.
[9]侯可佳,白晓颖,陆皓,等,基于接口语义契约的Web服务测试数据生成[J].软件学报,2013.24(9):2020-2041.
[10]HOU J,ZHOU H, MA C, et al.Method for automatically generat-ing test cases for web services[J].Journal of Northwestem Poly-technic al University, 2018, 36(1):149-155.
[11]王翀,呂荫润,陈力,等.SMT求解技术的发展及最新应用研究综述[J].计算机研究与发展,2017,54(07):1405-1425.
[12] MOURA LD,BJRNERN."23: An efficient SMT solver,”[C].in Proceedings of the Intemational conference on Tools and Algo-rithms for the Construction and Analysis of Systems, 2008: 337-340
[13]XEGER[EB/OL]( 2017 -06 -24) [2018 -03 -19]. https: //github.com/bluezio/xeger.