CUNIT的测试框架

  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

共享库应用举例

代码续
U_TestInfo suite_tests[] = { {"0. db infoamtion {"1. strlen function CU_TEST_INFO_NULL };
", test_dbinfo}, ", test_strlen},
//modify the foo_test to your module name #define MODULE_NAME foo_test char suite_name[] = DEFINE_MODULE_NAME(MODULE_NAME); int init_suite(void) { printf ("\ninit_suite: %s\n", suite_name); return 0; } int cleanup_suite(void) { printf ("\ncleanup_suite: %s\n", suite_name); return 0; } suite_struct DEFINE_MODULE_STRUCT_NAME(MODULE_NAME) = { suite_name, suite_tests, init_suite, cleanup_suite };
编译运行
编译 gcc -o libdl_func.so -fPIC -rdynamic -shared dl_func.c gcc -o dl_demo -fPIC -ldl dl_demo.c 运行 ./dl_demo 输出 calling add Hello, CUNIT Test Framework! 10 + 20 = 30
CUNIT结构
Test Registry
Suite „1'


Suite 'N'
Test '11'
……
Test '1M'
Test „N1'
……
Test „NM'
CUNIT的使用
1.
2.
3. 4. 5.
6.
编写测试函数(如果需要,则应编写 init/cleanup 函数). 初始化测试registry CU_initialize_registry() 添加suites至测试registry - CU_add_suite() 添加tests至suites - CU_add_test() 选择适当接口运行测试,如选择 CU_console_run_tests() 清理测试registry - CU_cleanup_registry()
*** CUNIT BEGIN *** CUnit - A Unit testing framework for C - Version 2.1-0 http://cunit.sourceforge.net/ Suite: foo_test Test: 0. db infoamtion ... passed Test: 1. strlen function ... FAILED 1. src/suite_foo_test.c:19 - CU_ASSERT_EQUAL(3,strlen("NHN CHINA")) --Run Summary: Type Total Ran Passed Failed suites 1 1 n/a 0 tests 2 2 1 1 asserts 7 7 6 1 *** CUNIT END ***
四种用户接口
接口 Automated Basic Console Curses 平台 所有 所有 所有 说明 非交互模式,输出为 XML文件 非交互模式,可以选 择输出到标准输出 控制台交互模式
Curses界面的交互模 Linux/Unix 式
Leabharlann Baidu
CUNIT事例

CUNIT:官方事例 http://cunit.sourceforge.net/example .html
共享库代码举例
源代码文件名:suite_foo_test.c 包含的头文件: #include <string.h> #include "suite_test.h" 2个测试(测试函数): void test_dbinfo() { PRINT_FUNCTION_START (); printf("host: %s, user: %s, passwd: %s, dbname: %s, port: %d\n", host, user, passwd, dbname, port); CU_ASSERT_PTR_NOT_NULL(host); CU_ASSERT_PTR_NOT_NULL(user); CU_ASSERT_PTR_NOT_NULL(passwd); CU_ASSERT_PTR_NOT_NULL(dbname); CU_ASSERT_TRUE(port > -1); PRINT_FUNCTION_END (); } void test_strlen() { PRINT_FUNCTION_START (); CU_ASSERT_EQUAL(4, strlen(“CUNIT")); CU_ASSERT_EQUAL(4, strlen(“CUNIT Test Framework")); PRINT_FUNCTION_END (); }
测试函数与assertions


CUnit中的测试”test”就是一个C语言中的函数, 其具有以下原型: void test_func(void) CUnit提供了一系列Assertions进行逻辑判断 在CUnit中,Assertions以宏定义方式提供 常用的Assertions: CU_ASSERT_TRUE(value) CU_ASSERT_EQUAL(actual, expected) CU_ASSERT_NOT_EQUAL(actual, expected) CU_ASSERT_STRING_EQUAL(actual, expected)
共享库入口协议
定义: typedef struct { /** The name of the suite */ const char *suite_name; /** The list of test info */ const CU_TestInfo *suite_tests; /** The suite initialization function.*/ int (*init_suite)(); /** The suite cleanup function. */ int (*cleanup_suite)(); } suite_struct; 入口程序加载共享库后,通过与共享库名称有关的变量名来获取代表 Suite 的suite_struct结构 共享库名称、suite名称与suite_struct结构名称的关系: 假设suite 名称为 foo_test, 那么suite_struct结构名称为suite_foo_test, 共享库名称为suite_foo_test.so

测试框架
= CUNIT + 共享库
基本思路

一个CUNIT 的 suite 对应一个 Linux共享库,即一个.so 文件代表一个suite 编写一个入口程序,负责:
• • • • 动态加载Linux共享库 从加载后的共享库中获取相关信息并组织成一个suite 初始化和清理registry,将suite添加到registry 根据配置文件选择如何运行测试
基于CUNIT的测试框架
李飞鹏 li.zhongnan@hotmail.com 2008年12月30日
内容



1、CUNIT 介绍 2、Linux下的共享库 3、CUNIT + 共享库 = 测试框架 4、移植到Windows 5、讨论
1、CUNIT 介绍
CUNIT是什么?


#include <stdio.h> #include <dlfcn.h> char name[100]; int main(int argc, char *argv[]) { int a = 10, b = 20; int c = 0; void *dlh = NULL; int (*add)(); strcpy(name, “CUNIT Test Framework"); if((dlh = dlopen("libdl_func.so", RTLD_LAZY)) == NULL) { fprintf (stderr, "***DL ERROR: %s.\n", dlerror ()); return 1; } if((add = (int (*)())dlsym(dlh, "add")) == NULL) { fprintf (stderr, "***DL ERROR: %s.\n", dlerror ()); return 1; } c = add(a, b); printf("%d + %d = %d\n", a, b, c); dlclose(dlh); return 0; }
Linux下的共享库
相关文件与函数

一个头文件:#include <dlfcn.h> 四个动态链接函数: (1) dlopen:将共享目标文件打开并且映射到 内存中,并且返回句柄 (2) dlsym:返回一个指向被请求入口点的指 针 (3) dlerror :返回 NULL 或者一个指向描述 最近错误的 ASCII 字符串的指针 (4) dlclose:关闭句柄并且取消共享目标文件 的映射

代码文件




run_suite.c 入口程序 run_suite.h 定义共享库入口接口suite_struct suite_test.h 有用的宏定义以及配置信息变量,方便共享库使 用,每个共享库代码程序都应该包含该头文件 共享库代码文件 根据要测试的环境而编写
代码文件




run_suite.c 入口程序 run_suite.h 定义共享库入口接口suite_struct suite_test.h 有用的宏定义以及配置信息变量,方便共享库使 用,每个共享库代码程序都应该包含该头文件 共享库代码文件 根据要测试的环境而编写

可配置,通过配置文件 入口程序与共享库数据的交互(即接口或协议) 入口程序的用法: Usage: ./bin/run_suite <conf_file> [suite_lib_file | suite_lib_dir]...
框架结构示意
入口程序 (run_suite)
配置文件
共享库 1 (.so文件)
编译、运行

编译共享库: gcc -I. -I./include -I./src -I./CUnit/include -L./CUnit/lib -lcunit -fPIC -fprofile-arcs ftest-coverage -m32 -Wall -g -p -o ./bin/suite_foo_test.so src/suite_foo_test.c shared -rdynamic 运行: ./bin/run_suite ./conf/cci.conf ./bin/suite_foo_test.so 输出:
dl_func.c
#include <stdio.h>
extern char name[];
int add(int a, int b) { printf("calling add\n"); printf("Hello, %s!\n", name); return a + b; }
dl_demo.c


CUNIT是一个针对C语言的轻量级单元测试编写、 管理和运行工具 提供了许多灵活的用户接口方便C程序员进行基 本的测试 与平台无关,可以作为静态库或动态库链接到用 户测试代码中, 使用一个简单的方式构建测试框架,提供了一系 列丰富的assertions来测试基本数据类型 提供了多种不同接口来运行测试和生成测试报表 CUNIT是开源的,官方站点: http://cunit.sourceforge.net
Suite 1
……
共享库 N (.so文件)
Suite N
Test '11' … Test '1M'
Test „N1' … Test „NM'
配置信息

入口程序通过配置文件获取 共享库将其作为外部变量使用 配置信息的内容(例如,数据库连接信 息):
• extern • extern • extern • extern • extern char host[]; char user[]; char passwd[]; char dbname[]; int port;
相关文档
最新文档