哈库拉玛塔塔——tjitty

记录下网络上的精品测试技术文章 and 生活

统计

留言簿(8)

积分与排名

阅读排行榜

评论排行榜

LoadRunner测试过程中调用dll文件的制作与使用

         在Windows操作系统中使用DLL有很多优点,最主要的一点是多个应用程序、甚至是不同语言编写的应用程序可以共享一个DLL文件,真正实现了资源"共享",大大缩小了应用程序的执行代码,更加有效的利用了内存;使用DLL的另一个优点是DLL文件作为一个单独的程序模块,封装性、独立性好,在软件需要升级的时候,开发人员只需要修改相应的DLL文件就可以了,而且,当DLL中的函数改变后,只要不是参数的改变,程序代码并不需要重新编译。这在编程时十分有用,大大提高了软件开发和维护的效率。

       在LR下也可以直接调用动态链接库文件,针对一些使用LR脚本编写比较烦琐的方法可以考虑此方法(比如各种加解密算法的实现,数据库的操作等),并能够使测试脚本简单明了。鉴于此,本人初次尝试了如何制作DLL文件并在LR中使用。

       1、dll文件的制作

       在Visual C++6.0开发环境下,打开File-New-Project选项,可以选择Win32 Dynamic-Link Library来创建一个名为dllfortest的空的dll工程(这只是方法之一)。

       在该项目中新建一个dllfortest.h和dllfortest.cpp文件,文件的内容如下:

//dllfortest.h

extern "C" _declspec(dllexport) int Max(int a, int b, int c);

extern "C" _declspec(dllexport) int Min(int a, int b, int c);

 

//dllfortest.cpp  包含一个计算三个整数中最大值和最小值的方法

#include"dllfortest.h"

int Max(int a, int b, int c)

{

       int Res;

       Res = (a>b? a:b)>c? (a>b? a:b):c;

       return Res;

}

int Min(int a, int b, int c)

{

       int Res;

       Res = (a>b? b:a)>c? c:(a>b? b:a);

       return Res;

}

该动态链接库编译成功后,打开dllfortest工程目录下的debug目录下,可以看到生成了一个dllfortest.dll文件,这就是我们想要的文件。

       2、dll文件在LR中的调用

       打开LR VU Generator,选择C Vuser协议(或其他支持C的协议),进入编辑界面。Action部分如下所示:

Action()

{

       lr_load_dll("dllfortest.dll");

       lr_message("Max Result is %d",Max(100,200,67));

       lr_message("Min Result is %d",Min(55,97,63));

       return 0;

}

将dllfortest.dll文件复制到脚本所在的目录(如果不复制的话,lr_load_dll的参数应该写成dll文件的绝对路径),如果编译没有报错的话,就可以直接运行了。

运行结果如下:

Virtual User scrīpt started

Starting action vuser_init.

Ending action vuser_init.

Running Vuser...

Starting iteration 1.

Starting action Action.

Max Result is 200

Min Result is 55

Ending action Action.

Ending iteration 1.

Ending Vuser...

Starting action vuser_end.

Ending action vuser_end.

Vuser Terminated.

 

如果在脚本中用到了DLL文件中并不存在的方法名时,编译也能通过,但是运行时LR会报错,提示不存在该方法

比如我们在脚本中添加一句:

       lr_message("Min Result is %d",Sum(55,97,63));  //Sum方法并不存在

运行时错误信息如下:

Action.c(7): Error: C interpreter run time error: Action.c (7):  Error -- Unresolved symbol : Sum.

Action.c(7): Notify: CCI trace: Compiled_code(0): Action()

.

这个例子并没有体现出DLL文件调用的优点,因为调用的方法在LR中用C直接就可以完成,但涉及到LR中完不成的任务时,或许dll文件的作用就体现出来了

example:
LoadRunner提供了功能强大的API集合,足够应付大多数性能测试的需求。但在某些情况下,这些API仍然有覆盖不到的地方。例如,我们有一个WEB应用,该应用有一个页面输入用户的信息,为了安全起见,用户输入的信息在提交之前都要先进行加密处理,加密处理通过本地的COM组件实现。

对这个要求而言,LoadRunner的现有API不能提供直接支持,因为LoadRunner在录制脚本时只录制数据交互,因此,COM的加密处理过程是不能录制下来的。在LoadRunner的脚本中,可能只有类似以下的语句描述了这个过程:

…………
web_url("userinfo",
    "URL=http://testweb/userinfo.aspx",
    "TargetFrame=",
    "Resource=0",
     "Referer=",
     LAST);

web_submit_form("login ",
"Snapshot=t4.inf",
ITEMDATA,
"Name=username", "Value=4e92Sh6d394g", ENDITEM,
"Name=password", "Value=932A2hf34U18", ENDITEM,
LAST);
…………

从脚本可以看到,输入的数据是加密后的数据,但LR没有录制到加密过程。

假设加密函数所在的DLL名为security.dll,用于加密的函数名为encode,则一种可能的对脚本的修改方法如下代码所示。
…………
char *encode_username, *encode_password, *orgin_username, *orgin_password;
char* uservalue, passvalue;
int ret;
……
web_url("userinfo",
     "URL=http://testweb/userinfo.aspx",
     "TargetFrame=",
     "Resource=0",
      "Referer=",
      LAST);

orgin_username = lr_eval_string(“{ username }”); //获取参数的值
orgin_password = lr_eval_string(“{ password }”);

ret = lr_load_dll(“security.dll”);   //加载DLL库

encode(origin_username, encode_username);  //调用encode函数
encode(origin_password, encode_password);


sprintf(uservalue, “Value=%s”, encode_username);
sprintf(passvalue, “value=%s”, encode_password);

web_submit_form("login ",
  "Snapshot=t4.inf",
  ITEMDATA,
  "Name=username", uservalue, ENDITEM,
  "Name=password", passvalue, ENDITEM,
  LAST);


注意:有些脚本录制需要相应的patch的支持,如录制DotNet编写的应用程序你需要把lr78安装盘\ Patches\Trap_for_.net_patch文件夹中trpfnc32.32dll拷贝到loadrunner\bin路径下,才能正常工作。

posted on 2008-03-13 19:41 tjitty 阅读(2231) 评论(0)  编辑 收藏 引用 所属分类: LoadRunner

只有注册用户登录后才能发表评论。