51Testing软件测试论坛

 找回密码
 (注-册)加入51Testing

QQ登录

只需一步,快速开始

微信登录,快人一步

查看: 3236|回复: 6
打印 上一主题 下一主题

[原创] 在AC上开发和运行QTP自动化测试脚本

[复制链接]

该用户从未签到

跳转到指定楼层
1#
发表于 2010-11-29 10:03:17 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
本帖最后由 sunshinelius 于 2010-11-29 10:08 编辑

AC应用案例:金融系统自动化测试


对于金融业务系统来说,测试案例往往涉及到数据校验,交易确认,业务关联等等,手工测试执行起来比较复杂,更不用提自动化测试的实施了。这也是当前金融系统业界功能自动化测试程度不高的原因之一。


1 金融系统业务测试的复杂性

比如某个银行支付系统的转账案交易,手工测试大概的流程如下:

1. 创建Test Account AAccount B,并在各自名下建立相应权限的转账卡

2. 使用Account A登录银行转帐系统,使用名下某一张卡对Account B做转账交易,支付金额为1000元人民币.

3.
查看Account AB的余额,确认A账户减少1000元,B账户上增加1000元。


以上三个步骤从银行业务角度来看是各自独立的三个功能,但在转账场景里,又有密切的联系。步骤2依赖于步骤1的先决运行,步骤3则需要步骤2的转账数据。

使用QTP等工具针对以上案例开发脚本,则会面临棘手的问题,如果把三个功能写在一个脚本里,就会大大降低每个功能脚本的复用性。若开发成三个不同的脚本,那么彼此的关系和数据交互又需要增加额外的开发成本来实现。


2使用AC的观点完成TestJob的定义

AC的世界里,一切都得非常简单,三个功能将被定义成三个TestJob

Create_Account_Info负责创建测试账户AB,然后将accountAaccountB作为参数输出。 AC中做如下定义:


  1. <QTP name="Create_Account_Info" description="以管理员身份登录后台系统创建测试账户及相关卡信息 " depends="" >
  2.          <JobOutput name="accountA"/>
  3.           <JobOutput name="accountB"/>
  4.            <Lib location=”common\lib\lib_utility.vbs”/>
  5.             <Run path="testcase\qtp\admin_createaccount"></Run></QTP>
复制代码

其中admin_createaccount是录制好的qtp脚本路径, lib_utility.vbs是脚本使用到的lib文件,AC将会自动加载到QTP运行环境中。

Transfer_FromAToB则会运行转账交易,将account A里的款项转给account B,并将转账数额作为参数输出。在AC中做如下定义:


  1. <QTP name="Transfer_FromAToB" description="以账户A登录,转账给B账户"  depends=""Create_Account_Info" >
  2.            <JobInput name="accountA"/>
  3.            <JobInput name="accountB"/>
  4.          <JobOutput name="transfer_amount"/>
  5.         <Lib location=”common\lib\lib_utilityvbs”/>
  6.             <Run path="testcase\qtp\transfer_bank"></Run>
  7. </QTP>
复制代码

Verify_Account根据输入的两个account信息和转账金额,检查account的余额是否预期变化。在AC中做如下定义:


  1. <QTP name="Verify_Account " description="检查账户A和账户B的余额是否预期变化 " depends="" Transfer_FromAToB " >
  2.         <JobInput name="transfer_amount"/>
  3.         <JobInput name="accountA"/>
  4.           <JobInput name="accountB"/>
  5.          <Lib location=”common\lib\lib_utilityvbs”/>
  6.            <Run path="testcase\qtp\transfer_bank"></Run>
  7. </QTP>
复制代码


以上三个TestJobAC组织起来,将会根据depends关系计算出执行路径:

Create_Account_InfoTransfer_FromAToBVerify_Account

同时,AC搭建一条全局数据通道,所有TestJobJobInputJobOutput等数据都可在这条通道中进行交互。针对QTP脚本,AC提供了框架vbs 函数writeDataIntoACChanel(paraname,paravalue)getDataFromChannel(paraname)实现写入和读出全局数据的功能。

上面谈到的是一种理想的TestJob结构模型,在实际的业务中,还有一些比较复杂的因素。比如,Create_Account_Info创建测试账户,测试卡号等信息这些工作,更合适在产品实例安装结束之后,作为基础数据被sql脚本直接创建至Database中。

这时,我们可将Create_Account_InfoQTP改由Java类型,而接口维持不变。


  1. <Java name="Create_Account_Info" description="Java程序调用jdbc运行sql脚本,在数据库中创建基础数据" depends="" >
  2.        <JobOutput name="accountA"/>
  3.          <JobOutput name="accountB"/>
  4.          <ClassPath location=”javacase\jdbc_sql.jar”/>
  5.            <Run path="jdbc.createAccount"></Run>
  6. </Java>
复制代码

其中jdbc.createAccount是按照AC规范自开发的java程序,调用jdbc运行sql脚本。

这种好处显而易见,Create_Account_InfoQTP转换成Java类型之后,只要接口维持不变(JobOutput不变),那么其它两个TestJobTransfer_FromAToBVerify_Account不会受到任何影响。

同理,Verify_Account也可改写成Java或者selenium类型,以不同的方式进行验证。

另外一种复杂的情形可能会出现在QTP层面上,如果QTP的脚本规模较大,而又在同一个产品实例的上下文中完成不同的功能。比如,登录后做查账,查账之后做理财交易等等,都是基于一个web session上完成的。针对这种情况,ACQTP提供了一种Factory Mode(工厂模式)的开发方式,使得所有的测试案例的定义和执行可以在同一个QTP执行环境中完成,非常适合QTP大规模的脚本开发工作。


3.AC提供QTP的工厂开发模式

基于录制生成的QTP脚本,是面向功能的,而不是结构化的测试案例。这使得QTP在维护和增加测试案例时,成本十分昂贵。为此,AC引入工厂开发模式,使得QTP的开发像Junit一样清晰方便。

QTP的工厂开发模式有如下规范:

1.每个QTP的测试案例在表现形式上都是一个Vbscript的函数,测试案例的增加/删除通过增加/删除一个VBSFunction来达到。

2.工厂模式不支持对象库模式的脚本,所有的功能都以Description编程来实现

3.使用checkDependence函数来检查每个测试案例的运行结果状态

4.调用writeIntoACChannelgetDataFromChannel来完成测试案例之间的数据交互。

5.每个测试案例都是一个函数,一个函数是否成为一个测试案例取决于在TestJobFile.xml中的定义。


示例:

QTP自带的Flight演示程序,录制生成的脚本如下模式:


  1. ‘登录客户端Dialog("Login").WinEdit("Agent Name:").Set "testing"Dialog("Login").WinEdit("Password:").Set "mercury"Dialog("Login").WinButton("OK").Click‘输入机票信息,下订单Window("Flight Reservation").ActiveX("MaskEdBox").Type "081210"Window("Flight Reservation").WinComboBox("Fly From:").Select "Frankfurt"Window("Flight Reservation").WinComboBox("Fly To:").Select "London"Window("Flight Reservation").WinButton("Insert Order").ClickWindow("Flight Reservation").Close
复制代码


QTP录制脚本转换成工厂模式脚本,步骤如下:

1.创建一个testcase.vbs

2.将原始脚本进行description改写,并按照工厂模式规范,写入testcase.vbs


登录测试案例


  1. Function login
  2. '调用框架函数ReportRunningInfo,写日志
  3. ReportRunningInfo "start to run login test case"
  4. ……………Description创建……………………
  5. Dialog(dlgLoginDesc).WinEdit(editUserDesc).set getDataFromACChannel("user")
  6. Dialog(dlgLoginDesc).WinEdit(editPasswdDesc).set getDataFromACChannel("passwd")
  7. Dialog(dlgLoginDesc).WinButton(btnOKDesc).Click
  8. if(Window(flightWindowDesc).Exist(30)) Then
  9. ‘调用reportPass,向AC报告当前案例成功状态
  10. reportPass "has sigin in successfully"
  11. login = True
  12. Else
  13. ‘调用reportFail,向AC报告当前案例失败状态
  14. reportFail "failed to sigin in"
  15. login = False
  16. End If
  17. '将用户名写入数据通道,供后续执行的测试案例使用.

  18. username = "sheng.liu"
  19. writeIntoACChannel "displayname",usernameEnd Function
复制代码

     订机票测试案例


  1. Function bookFlight
  2. ReportRunningInfo "start to run book flight test case"
  3. '检查login案例是否成功,如果失败,当前案例则返回失败.
  4. If Not CheckDependence("login") Then
  5. bookFlight = False
  6. Exit Function
  7. End If
  8. …………..Description创建及调用……………………
  9. '从数据通道中获得login案例写入的用户名,作为订单用户名下单.
  10. username = getDataFromACChannel("displayname")
  11. Window(flightWindowDesc).WinEdit(nameEditDesc).Set usernameWindow(flightWindowDesc).WinButton(insertBtnDesc).Click
  12. ……………………….End Function
复制代码


3.定义TestJobFile.xml文件,指定工厂模式和测试案例



  1. <QTP name="QTP_DesktopClientTest_AC" description="demo" factoryMode="true" depends="Java_Init" iteration="">
  2.       <Lib location="testscripts\DesktopClient\testcase.vbs"/>
  3.        <Testdata type="xsl" location="data\data_global_shining.xls"/>
  4.        <Testdata type="xsl" location="data\data_global_shining.xls"/>
  5.          <Testdata type="iteration" location="data\testdata.xls"/>
  6.       <Case name="test.vbs" description="demo" depends="">
  7.            <Test name="login"description="login flight app"><Run path="login"/></TestJob><Test name="bookFlight" description="book flight"><Run path="login"/></TestJob>
  8. </Case>
  9. </QTP>
复制代码


4.运行AC框架


AC会从指定的lib路径中获得testcase.vbs,然后以工厂模式运行loginbookflight两个测试案例。并最终形成测试报告。


从上面的示例可以看出,经过工厂模式改写后,QTP自动化测试具有以下优势

1.测试案例的粗细粒度更加细微,可以有效地与手工测试案例形成一一对应的映射关系

2.扩展性大大增强,增加新的功能点,只需开发新的function函数即可集成到AC中。

3. 案例之间的依赖关系和数据交互更加密切。


总之,工厂模式非常实用于大规模的QTP的自动化测试脚本开发,大大减少维护成本,提升开发效率。


Automation Center免费,并逐步在www.cesoo.info发布开源,详情了解

http://www.cesoo.info/bbs/

分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友
收藏收藏
回复

使用道具 举报

该用户从未签到

2#
发表于 2010-12-1 16:26:29 | 只看该作者
虽然有些新意!但是太繁琐了!如其这样,我还不如直接在QTP中去写呢!
回复 支持 反对

使用道具 举报

该用户从未签到

3#
 楼主| 发表于 2010-12-2 22:21:18 | 只看该作者
录制回放的qtp脚本适合周期短,上手快的项目。
要是想开发稳定大规模的qtp脚本,那就必须在效率和结构中做一个平衡
回复 支持 反对

使用道具 举报

该用户从未签到

4#
发表于 2010-12-6 15:46:57 | 只看该作者
我并不是指的是录制回放,我看了你的东西,实际你搭了一个框架,但是里面所有的实现由我们来做!但是你的框架搭建的比较繁琐,我是这样理解的!如果我们的思路和你的思路相同,那么你的框架帮我少写了很多程序!但是我们不需要你那么多的东西或者说想法不同的话,反而会增加我们的工作量!
比如说:你所指的描述性编程,我们也采取描述性编程模式来做!但是如果使用你们的模式,那么就必须要按照你的约定,先做定义这个对象约定来做,否则就不可行,
还有比如说我们有很多的数据控制,我们写了很多的数据处理方法,数据都是保存在数据库中,而且编写了很多QTP接口来调用数据,但是你们采取xls驱动也就很难满足像我们这些企业级,多类数据源的客户的。
所以我觉得你这个有很多借鉴的地方,但是我觉得你这个框架更加适用于与你思路相同或者相仿的人,或者说尚未开始自动化模式的人,如果像我们这样做过多年,然后像你们这边靠的化,反而麻烦了!
我觉得你的思想很不错!我反而建议你模块独立化,不一定采取你的这个模式来实现整体化的东西
回复 支持 反对

使用道具 举报

该用户从未签到

5#
 楼主| 发表于 2010-12-9 21:44:35 | 只看该作者
回复 4# testhellen

呵呵,看来上面的朋友是做过多年自动化测试的朋友了。所以咱们直奔主题了来具体问题具体讨论
1. depedency(约定)是为了减少自动化测试失败可能带来的浪费时间。假设B案例依赖于A案例,A失败了,则B可不必运行。实际上,我们在设计测试案例的时候也是遵循高内聚,低耦合的设计原则,尽量使每个案例独立而单一,但实际上很难做到,所以引入dependency的概念。
2. 如果测试一个比较复杂的应用,比如web系统,各个测试案例的运行其实上是基于一个web session的。如果按照传统的qtp脚本的话,某些session初始化的操作必然会被重复调用多次,比如登录等。因为qtp一旦启动,又关闭,上下文就消失了。factory模式的一个作用就是解决这个问题,其实所有的function都是基于一个session完成的,理论上,只要安排得到,所有的测试案例脚本都可以在保证无重复性的被调用。您如果有好的想法,我愿意虚心学习
3. 至于数据驱动从db,xml还是xsl走,这是一个低层的问题,能够符合业务需求就是最好的解决方案。我的企业里,qtp的脚本行数超过10万行了,一直用xml数据源也很好。
另外,在Automation Center里,qtp只是其中一个job engine,还有selneium engine,jdbc engine,java engine。我个人建议,基础数据工作如果庞大,其创建和读取更合适独立出来,放在jdbc job里, 而qtp job和jdbc job做一个dependecy定义,数据通过框架的数据通道传递。QTP只关心业务的操作,jdbc只负责数据的处理,这样更显清晰。

希望听到您的意见!
回复 支持 反对

使用道具 举报

该用户从未签到

6#
 楼主| 发表于 2010-12-9 21:53:50 | 只看该作者
实际上,vbscirpt由于其脚本解释执行的效率低下,脆弱的错误处理能力,大规模脚本难以调试的特点,应该对vbscript的规模加以限制。我个人看法是,凡是和qtp object model调用无关的操作,尽量使用编译语言来完成, 比如数据的读取,qtp的驱动,结果报告的生成,完全可以通过技术手段绕开vbscirpt,以获得健壮性。
Automation Center就是纯java开发。呵呵。
回复 支持 反对

使用道具 举报

该用户从未签到

7#
 楼主| 发表于 2010-12-9 22:30:44 | 只看该作者
回复 4# testhellen
如果方便,能否说下您的产品测试有什么特点,qtp的具体解决方案是怎样的。
回复 支持 反对

使用道具 举报

本版积分规则

关闭

站长推荐上一条 /1 下一条

小黑屋|手机版|Archiver|51Testing软件测试网 ( 沪ICP备05003035号 关于我们

GMT+8, 2024-5-2 00:21 , Processed in 0.078577 second(s), 27 queries .

Powered by Discuz! X3.2

© 2001-2024 Comsenz Inc.

快速回复 返回顶部 返回列表