基于Lua脚本的自动化测试框架设计



一、自动化测试背景

1. 被测对象为嵌入式系统中使用Lua脚本做胶合的一个个模块接口。需要编写Lua脚本调用这些接口对接口进行测试,运行环境为嵌入式系统中并非PC机。

2. 测试脚本能够起到回归测试及自动判断测试结果和输出测试报告

二、实现方法

主要参考XUnit框架机制实现测试套的封装,其封装的对象如下:

1. 测试环境

2. 自动化判断

3. 测试日志

4. 测试执行情况统计

5. 测试报告

三、测试框架

1. InitTestFrame()                        --初始化测试框架 ,只能执行一次,否则会影响测试结果统计 
2. SetCurrModule("CurrModuleName")      --当前测试模块的名字 
3. WriteCaseName("CurrCaseName")        --当前测试用例的名字 
4. WriteCaseStep("CurrStepName")          --当前测试步骤的名字 
5. ret = AssertResult("sExpects","RealResult")  --自动比较(选用) 
6. WriteReport(ret,"sRealResult")            --将测试结果写入测试报告文件中 
7. GetStatistic()                          --获取测试执行情况统计 

四、实现代码

1. 环境变量

 --定义不同的环境变量,便于脚本的移植 
  if TestEntironment == nil then  --如果没有定义TestEntironment 
      Win32   = 1 
      Symbian = 2 
      TestEntironment = Win32 
      --TestEntironment = Symbian 
  End 
   
  if TestEntironment == Win32 then 
      reportfile = "..\\TestCode\\TestReport.txt"  --测试报告文件 
  else 
      reportfile = "c:\\TestCode\\TestReport.txt"  --测试报告文件 
  end 

2. 初始化测试框架

 --初始化测试框架 
  function InitTestFrame() 
      --定义存储各模块测试执行情况的表 
      tRunStatistic = {} 
      tRunStatisticIndex = 0   --tRunStatistic的索引 
       
      CurrNGModuleIndex  = 0 
      CurrNGCaseIndex    = 0    
      --定义存储执行失败用例的表 
      tRunNG = {} 
  end 

3. 测试套封装 

function WriteCaseName(sCaseName)   --标记测试用例名,写入测试报告文件  
      CurrCase = sCaseName  
      local h = io.open(reportfile,"a")  
      io.output(h)  
      local sWriteStr = "\n【" .. sCaseName .."】" .. "\n"  
      if TestEntironment == Win32 then  
          print(sWriteStr)      
      end   
      io.write(sWriteStr)  
      io.close(h)  
  end  
  function WriteCaseStep(sStep)   --标记测试步骤,写入测试报告文件  
      CurrStep = sStep  
      local h = io.open(reportfile,"a")  
      io.output(h)  
      local sWriteStr = "   |--" .. sStep .. "\n"  
      if TestEntironment == Win32 then  
          print(sWriteStr)      
      end   
      io.write(sWriteStr)  
      io.close(h)  
  end  
  function SetCurrModule(sModuleName)  
      CurrModule  = sModuleName  
      temp        = {Module = sModuleName,iRunCaseNum = 0,iOKCaseNum = 0,iNGCaseNum = 0}  
      tRunStatisticIndex = tRunStatisticIndex + 1  
      table.insert(tRunStatistic,tRunStatisticIndex,temp)  
  end  

4. 自动化判断

--自动比较期望结果与测试结果   
  function AssertResult(sExpects,RealResult)  
      if sExpects == RealResult then  
          return "OK"  
      else   
          return "NG"  
      end  
  
  end

5. 测试日志

 function WriteMsg(sMsg)  
      local h = io.open(reportfile,"a")  
      io.output(h)  
      local sWriteStr = sMsg .. "\n"  
        
      if TestEntironment == Win32 then  
          print(sWriteStr)      
      end   
        
      io.write(sWriteStr)  
      io.close(h)  
  end

6. 测试报告

--将测试结果写入测试报告文件  
  function WriteReport(sAssertResult,sRealResult)  
      local h = io.open(reportfile,"a")  
      io.output(h)  
      local sWriteStr = "       " .. sAssertResult .."    (RealResult:" .. sRealResult .. ")\n"  
        
      if TestEntironment == Win32 then  
          print(sWriteStr)      
      end   
     
      io.write(sWriteStr)  
      io.input(h)  
      io.close(h)  
        
      AddRunStatistic(sAssertResult)  
  end  

7. 测试执行统计

function AddRunStatistic(sAssertResult)  
      --统计测试执行情况  
      tRunStatistic[tRunStatisticIndex].iRunCaseNum = tRunStatistic[tRunStatisticIndex].iRunCaseNum + 1  
      if sAssertResult == "OK" then  
         tRunStatistic[tRunStatisticIndex].iOKCaseNum = tRunStatistic[tRunStatisticIndex].iOKCaseNum + 1  
      else  
         tRunStatistic[tRunStatisticIndex].iNGCaseNum = tRunStatistic[tRunStatisticIndex].iNGCaseNum + 1  
           
         --将失败的插入tRunNG  
         if (tRunNG[CurrNGModuleIndex]~= nil)and(tRunNG[CurrNGModuleIndex][1] == CurrModule) then  --存在Module记录  
             if (tRunNG[CurrNGModuleIndex] [2][CurrNGCaseIndex][1]~= nil)and(tRunNG[CurrNGModuleIndex][2] [CurrNGCaseIndex][1] == CurrCase) 
 then --存在Case记录  
                 --添加Step项  
                 table.insert(tRunNG[CurrNGModuleIndex][2][CurrNGCaseIndex][2],CurrStep)  
             else  
                 --增加Case项  
                 table.insert(tRunNG[CurrNGModuleIndex][2],{CurrCase,{CurrStep}})  
                 CurrNGCaseIndex = CurrNGCaseIndex + 1  
             end  
         else --增加Module项  
             table.insert(tRunNG,{CurrModule,{{CurrCase,{CurrStep}}}})  
             CurrNGModuleIndex = CurrNGModuleIndex + 1  
             CurrNGCaseIndex   = 1  --复位1  
         end  
      end   
  end  
    
    
  --统计测试用例执行情况  
  function GetStatistic()    
      WriteMsg("\nTestcase run statistic:")  
      WriteMsg("**********************************************************************")  
      WriteMsg("【ModuleName】".."          【Run】".."          【OK】".."          【NG】")  
      WriteMsg("----------------------------------------------------------------------")  
      for i = 1,table.getn(tRunStatistic) do  
          --打印格式  
          s1 = ""  
          for j = 1,24 - string.len(tRunStatistic[i].Module) do  
              s1 = s1 .." "  
          end  
          s2 = ""  
          for j = 1,17 - string.len(tRunStatistic[i].iRunCaseNum) do  
              s2 = s2 .. " "  
          end  
          s3 = ""  
          for j = 1,16 - string.len(tRunStatistic[i].iOKCaseNum) do  
              s3 = s3 .. " "  
          end  
          WriteMsg(i..":"..tRunStatistic[i].Module..s1..tRunStatistic[i].iRunCaseNum..s2..tRunStatistic[i].iOKCaseNum..s3..tRunStatistic[i]
 .iNGCaseNum)  
      end  
      WriteMsg("**********************************************************************")  
      --记录执行失败用例  
      GetRunNGCase()  
  end  
  --记录执行失败用例       
  function GetRunNGCase()  
      WriteMsg("NG case info:")  
      if table.getn(tRunNG)==0 then  
          WriteMsg("No NG case,are you sure your case is perfect?")  
      end  
      for i = 1,table.getn(tRunNG) do  
          WriteMsg(tRunNG[i][1])   --Module Name  
          for j = 1,table.getn(tRunNG[i][2]) do  
              WriteMsg("  |--"..tRunNG[i][2][j][1]) --Case Name  
              for k = 1,table.getn(tRunNG[i][2][j][2]) do  
                  WriteMsg("        |--"..tRunNG[i][2][j][2][k])    -- Step Name  
              end  
          end  
      end  
  end 

五、使用方法 

1. 测试用例

function db_read_case()  
      WC("db_read_case");  
      WS("Step1")  
      h = db.open(U(Sdir .. "dbComm"))  
      --WM(h)  
      --读数据  读取全部   
      for i = 1,TEST_RECORD do  
          writeField = string.char(0x15)  
          for j = 1,20 do  
              writeField = writeField .. string.char(i+j)  
          end  
          readField = db.read(h,i,0,512)   --被测接口  
          ret = AR(writeField,readField)  
          if(ret == "NG")then  
              WM("error:".. i)  
              break  
          end  
      end  
  WR(ret,"nil")  
    
      --关闭打开的数据库  
      db.close(h)  
  end  
    
  --测试用例执行  
  InitTestFrame()  
  WriteMsg("Database API test begin ...")  
  SetCurrModule("Database")  
  CreateEntironment() --创建测试环境  
  db_read_case()  
  DestroyEntironment()--清除测试环境  
  WriteMsg("Database API test end!\n")  
  GetStatistic() 

2. 测试报告

****************************************************  
  Tester   :Anndy
  Test Date:03/27/08 15:19:06  
    
  Database API test begin ...  
    
  【db_read_case】  
     |--Step1  
         OK    (RealResult:nil)  
     |--Step2  
         OK    (RealResult:nil)  
  Database API test end!  
    
  Testcase run statistic:  
  **********************************************************************  
  【ModuleName】          【Run】          【OK】          【NG】  
  ----------------------------------------------------------------------  
  1:Database                57               49              8  
  **********************************************************************  
  NG case info:  
  Database  
    |--db_read_case  
          |--Step1  
    |--db_update_case  
          |--Step4  

你可能感兴趣的:(性能测试)