loadrunner,socket脚本总结

 一、socket脚本编写的基本函数

lrs_startup 初始化 WinSock DLL

lrs_create_socket 初始化套接字

lrs_send 在数据报上(UDP)或者向流套接字(TCP)发送数据

lrs_receive 接收来自数据报或流套接字的数据

lrs_close_socket 关闭打开的套接字

lrs_cleanup 终止 WinSock DLL 的使用,回收相关资源。VuGen Windows 上使用 Windows 套接字协议支持应用程序的录制和回放;而在UNIX 平台上仅支持回放

lrs_free_buffer 释放分配给缓冲区的内存

lrs_get_last_received_buffer 获取套接字上接收到的最后的缓冲区及其大小

lrs_get_last_received_buffer_size 获取套接字上接收到的最后一个缓冲区的大小

lrs_set_recv_timeoutparam1param2)第一个参数是s,第二个参数是ms服务器响应超时

lrs_set_recv_timeoutsparam1param2)第一个参数是s,第二个参数是ms匹配收到报文长度

 

lrs_set_socket_options 设置套接字选项

lrs_set_receive_option 设置套接字接收选项

lrs_save_param将静态或者接收到的缓冲区(或缓冲区部分)保存到参数中

lrs_save_param_ex将用户、静态或接收的缓冲区(或缓冲区部分)保存到参数中

lrs_save_searched_string在静态或接收到的缓冲区中搜索出现的的字符串,将出现字符串的缓冲区部分保存到参数中

 

二、三个关联函数的介绍

lrs_save_param将静态或者接收到的缓冲区(或缓冲区部分)保存到参数中

lrs_save_param_ex将用户、静态或接收的缓冲区(或缓冲区部分)保存到参数中

lrs_save_searched_string在静态或接收到的缓冲区中搜索出现的的字符串,将出现字符串的缓冲区部分保存到参数中

(1) lrs_save_param

lrs_save_param("socket2","buf3","state",172,2);

lrs_save_param("socket2",NULL,"state",172,2);

建议用MULL,表示last receive buffer.

定位172位置的方法:选定buf3后按F7,转换成16进制后,找到你需要的字符,就可以定位了。

lr_error_message("error code is %s",lr_eval_string("<state>"));

Action.c(57): Notify: Saving Parameter "state = AA".

Action.c(58): Notify: Parameter Substitution: parameter "state" =  "AA"

Action.c(58): Error: error code is AA

2lrs_save_param_ex

例子:lrs_save_param_ex(socketID, "received", Buffer,0,NumberOfBytes, "ascii", "new_parameter");

int lrs_save_param_ex ( char *s_desc, char *type, char *buff, int offset, int length, char *encoding, char *param );

s_desc表示指定的Socket名称;

type表示要存储的数据类型,有“user”、“static”、“received”三种,分别代表用户数据(脚本中自己定义的字符串)、静态数据(data.ws中录制的数据)、最后接收的缓冲区数据;

buff表示要保存哪个缓冲区的数据。这个参数与type有对应关系,如果type是“user”、“static”两种,则需要指定具体的buffer名称;如果是“received”则可以忽略这个参数;

offset表示在buffer中的偏移量;

length表示要从buffer中保存的字节数;

encoding表示的是解码方式。对于“user”类型的buffer,需要指定其为ascii或者ebcdic中的一种,NULL值表示默认的格式为ascii。对于“static”与“received”两种类型的buffer,则可以忽略这个参数,使用客户端的原始编码格式来进行解码;

param表示要保存的参数名称。

3lrs_save_searched_string

lrs_save_searched_string ( char* s_desc, char* buf_desc, char* param_name, char* left_boundary, char* right_boundary, int ordinal, int offset, int param_len );

具体参数设置可看F1,帮助文档

lrs_save_searched_string("socket2", NULL, "p", "LB=AAAAAAA\\x01", NULL,1, 0, 2); FAIL

lrs_save_searched_string("socket2", NULL, "p", "LB/BIN=AAAAAAA\\x01", NULL,1, 0, 2);

lrs_save_searched_string("socket2", NULL, "p", "LB/BIN=\\x99\\a", NULL,1, 0, 2);

\”要转义,并要使用“LB/BIN”不能缺少BIN,左边界出现的次数;offset偏移字节;如果没有右边界则是截长度,否则为-1

小结:

1、    相同点:

三个函数都可以截取报文中的字符串。

2、    三者的区别

(1)lrs_save_param_exlrs_save_param的扩展函数,功能相对更全一些,两者均是根据偏移量和查找的数据的长度来定位所需要的数据,所以只适合于返回报文基本固定的情况;

(2)lrs_save_searched_string则是如web脚本里web_reg_save_param,能够根据左右边界灵活处理对于可变返回报文中的字符串;【需注意的是:web_reg_save_param要放在需要关联的请求前,而lrs_save_searched_string是放在请求后】

(3)lrs_save_searched_string函数对于一些特殊情况也是很方便,比如需统计一个字符串总共出现的次数。

 

三、关于脚本超时相关介绍

socket的脚本里面,我们在LG里面执行到lrs_receive的时候,回放脚本的时候(忽略think time 的情况下)发现脚本回放很慢。但事务的响应时间并不长。在generator的日志里面看到,(Duration: 10.3054 Wasted Time: 10.0000)。其中wasted time10秒。

这个wasted time 是开销在哪呢?先介绍2个函数:

lrs_set_recv_timeoutparam1param2)第一个参数是s,第二个参数是ms,执行lrs_receive命令后,等待服务器返回消息的超时时间,即服务器的响应时间。

lrs_set_recv_timeout2 创建连接成功,接收到服务器返回的消息后,获取匹配消息的超时时间。lrs_receive接收到数据后,会和预期的数据长度进行比较,如果长度不匹配,它将重新从套接字上读取数据,直到超时为止。

 

再来看前面的wasted time 就好理解了,在data.wsrecv  buf3 4010 buf3的长度原本预期为401,录制(或者设置)时接收buffer的大小(4010)和回放时接收的buffer大小预期(401)的不一样,lrs_set_recv_timeout2这个函数就会一直读取缓存区的值,在这里浪费10秒(默认为10秒)。

   

   另外:当我们把这样的脚本放到controller中去执行,执行的结果就是响应时间是正常的,但是TPS很低,原因就是对于这个waiting timeLR并不把这个时间计入到响应时间中,但对于TPS来说,发起的笔数就相对来说少了,这个wasted time 相当于智能的迭代时间。

对于接收报文固定长度的,建议recv buf 长度写成和预期的一致,避免不必要的开销。

但我们也有可能遇到socket返回的响应buffer是变长的, 使用lrs_set_receive_option函数设置返回的属性,来实现这种动态的数据缓冲。

lrs_set_receive_option(EndMarker, EndMarker_None ) // 读取直到缓冲结束.

lrs_set_receive_option(EndMarker, StringTerminator , "\r\n") //读取直到"\r\n"符号出现 .

lrs_set_receive_option(EndMarker, BinaryStringTerminator , "\X00") 读取直到二进制符号"\\X00"出现

此方法适用于知道返回数据包的最后符号的情况,接收过程中读取此符号即停止接收。

2.或者我们手工指定loadrunner脚本,捕获多长的buffer。就需要使用如下代码来代替lrs_receive lrs_receive_ex("socket1", "buf3", "NumberOfBytesToRecv=150", LrsLastArg); 到此为止,socket通讯单次的发送、接收应该基本没有什么问题了。至于多次交互涉及到的关联等技巧 

Another option is mismatch:lrs_set_receive_optionMismatchMISMATCH_SIZE

 

 

 

 

posted @ 2015-05-25 11:06  ccfly  阅读(1929)  评论(0编辑  收藏  举报