本文介紹了Reporter對象的幾個鮮為人知的方法,利用LogEvent、SetContext、UnSetContext方法,可以實現日志的結構化、層次化寫入,讓你的QTP測試報告看起來更加有條理、分類清晰。
QTP的日志其實有很多的缺點,尤其是當你的腳本依賴函數來執行的時候,因為函數執行時調用Reporter對象來寫日志,只會順序從上到下、扁平、不分類地寫下去,如圖1所示。
圖1 函數執行時調用Reporter對象寫日志的問題
而不像在Action中寫日志一樣,按一定的層次關系來寫日志(例如根據調用的關系嵌套)。那么如何讓函數調用Reporter對象來寫日志時也具備一定的層次關系,讓日志展現更加靈活、分類清晰呢?其實QTP的Report對象中暗藏了不少可利用的屬性和方法。
Report對象的“私家珍藏”
在關鍵字視圖通過InterlliSense查看QTP的Report對象時(如圖2所示),可發現僅有3個屬性、1個方法可用,其中最常用的是ReportEvent方法。
圖2 Reporter對象的公開方法和屬性
而實際上,QTP的Report對象還有其他的方法可用,這些方法并沒有對外公開,例如可用LogEvent方法來在日志樹中寫入一個節點:
' 使用Reporter對象的LogEvent寫入新節點
intContext = Reporter.LogEvent("User", dicMetaDescription, Reporter.GetContext)
用SetContext方法把某個節點作為父節點,這樣的話,后續寫入的Log都將在這個父節點之下:
' 調用Reporter對象的SetContext把新寫入的節點作為父節點
Reporter.SetContext intContext
如果要退出該節點,返回日志樹的上一層,則可調用UnSetContext方法即可,如下腳本所示:
'調用Reporter對象的UnSetContext,返回上一層
Reporter.UnSetContext
Report對象“解密”
有了LogEvent、SetContext、UnSetContext這幾個方法,我們就可以實現日志的結構化、層次化寫入了,例如下面的例子所示:
' 用一個Dictionary對象來存儲節點的信息
Set dicMetaDescription = CreateObject("Scripting.Dictionary")
' 設置節點的狀態
dicMetaDescription("Status") = MicDone
' 設置節點的名稱
dicMetaDescription("PlainTextNodeName") = "父節點"
' 設置節點的詳細描述信息(可以使用HTML格式)
dicMetaDescription("StepHtmlInfo") = "
' 設置節點的圖標
dicMetaDescription("DllIconIndex") = 210
dicMetaDescription("DllIconSelIndex") = 210
' 節點圖標從ContextManager.dll這個DLL文件中讀取
dicMetaDescription("DllPAth") = "D:\Program Files\HP\QuickTest Professional\bin\ContextManager.dll"
' 使用Reporter對象的LogEvent寫入新節點
intContext = Reporter.LogEvent("User", dicMetaDescription, Reporter.GetContext)
' 調用Reporter對象的SetContext把新寫入的節點作為父節點
Reporter.SetContext intContext
' 后續寫入的Log都將在這個父節點之下
Reporter.ReportEvent MicPass, "Step1", "Step1 Pass!"
Reporter.ReportEvent MicWarnning, "Step2", "Step2 Pass With Warnning!"
Reporter.ReportEvent MicFail, "Step2", "Step2 Fail!"
'調用Reporter對象的UnSetContext,返回上一層
Reporter.UnSetContext
' 在父節點之外寫Log
Reporter.ReportEvent MicPass, "Case2", "Case2 Pass!"
在這個例子中,我們首先用一個Dictionary對象來存儲節點的信息,其中Status表示節點的狀態,例如MicDone就表示完成狀態;PlainTextNodeName表示節點的名稱;StepHtmlInfo表示節點的詳細內容,可以用HTML格式來寫入;還可以用DllIconIndex、DllIconSelIndex、DllPAth這3個屬性來表示節點的圖標。
然后使用Reporter對象的LogEvent把Dictionary中存儲的信息寫入一個新節點,再調用Reporter對象的SetContext把新寫入的節點作為父節點,這樣后續寫入的Log都將在這個父節點之下,最后調用Reporter對象的UnSetContext,返回上一層,這樣后續寫入的Log將在這個父節點之外。
這個例子的運行結果如圖3所示。
圖3 腳本運行結果
封裝成可重用的函數
可以把上面的代碼封裝成一個可重用的函數,以方便調用。方法如下:
(1)首先在QTP中使用“Function Definition Generator”來定義一個名為“EnterNode”的函數。如圖4所示。
圖4 定義函數EnterNode
該函數實現的是把日志寫入某個節點下,輸入參數為NodeName(節點的名稱),NodeContent(節點的描述信息)。
函數的腳本如下:
原文轉自:http://www.anti-gravitydesign.com