輕量級API測試框架Pandaria
最近參與了一個專案,團隊有自動化測試訴求,但是測試人員沒有程式設計能力,開發人員也沒有精力幫忙,探索了已有的自動化測試工具,滿足不了團隊需求後,決定自己造個輪子。
Postman是一個不需要編碼能力,且十分方便的自動化測試工具,由於專案中很多測試的驗證點需要驗證資料庫裡面資料的正確性,如果用Postman的話需要為測試建立一些沒有必要的HTTP API。很遺憾, 這個輪子不滿足我們的要求。
- Rest-assured
我們探索的第二個工具是Rest-assured. 雖然他對API測試相關操作封裝了很簡潔美觀的DSL, 由於其直接是Java程式碼,像資料庫校驗什麼的毫無困難。但是要編寫基於Rest-assured的自動化測試,還得有一定的編碼基礎,很遺憾,這個輪子我們用不來。
- Cucumber
Cucumber支援自然語言形式編寫自動化測試,自然語言呼叫的是程式碼,如果對cucumber做了足夠好的封裝,編寫測試的人不需要編寫程式碼也能寫自動化測試。那就需要做足夠通用的封裝,所以Pandaria就是基於cucumber jvm封裝的HTTP(S) API自動化測試的DSL。Cucumber本身功能非常實用,使用pandaria依然能夠直接使用cucumber jvm的所有功能。
ofollow,noindex">Pandaria
在測試團隊缺乏編碼能力,以及需要驗證資料庫的需求背景下,我們嘗試著基於cucumber做封裝,使不會寫程式碼的測試人員也能編寫自動化測試。之後我們很驚訝的發現這種方式非常有效,所以將這個工具分享出來,希望能對有相同訴求的團隊有所幫助。
測試HTTP API
Scenario: simple get * uri: /users/me * send: GET * status: 200 * verify: '$.username'='jakim' * verify: '$.age'=18 複製程式碼
使用pandaria寫API自動化測試,就像上面這樣,只需要使用抽象好的關鍵字,描述傳送請求的過程,以及編寫你的驗證條件即可。
上述程式碼解讀: 往相對路徑uri為/users/me
的地址傳送GET請求,並驗證返回狀態為200,且返回體裡面json path為$.username
的值為'jakim'
,json path$.age
處的值為18
。
驗證資料庫
* query: """ SELECT NAME, AGE FROM USERS """ * verify: '$[0].name'='jakim' * verify: '$[0].age'=18 複製程式碼
或者
* query: select.sql * verify: '$[0].name'='jakim' * verify: '$[0].age'=18 複製程式碼
select.sql
SELECT NAME, AGE FROM USERS 複製程式碼
測試人員只用寫SQL就能像校驗json一樣校驗資料庫內容。上述程式碼會使用SQL語句SELECT NAME, AGE FROM USERS
到資料庫中查詢,並驗證返回結果的第1行的name
和age
屬性。
準備測試資料可以直接執行SQL檔案:
* execute sql: prepare_users.sql * execute sql: """ insert into users(name) values('test'); """ 複製程式碼
等待功能
自動化測試經常需要等待一件事情完成,特別是非同步操作時,這時候通常的做法是等待一定的時間,驗證結果,如果不通過,則重試一定的次數,直到驗證成功,或者超過最大次數失敗。使用Pandaria可以這麼寫:
* wait: 1000ms times: 3 * uri: /sequence * send: GET * response body: """ 3 """ 複製程式碼
上述程式碼會往/sequence
發請求,並驗證返回訊息體是否等於3
,如果等於則繼續往下執行,如果失敗則等待1000ms,然後重試,如果重試超過最大3
次,則測試失敗。
也可以等待資料庫中資料滿足某個條件
* wait: 1000ms times: 3 * query: select.sql * verify: '$[0].name'='jakim' * verify: '$[0].age'=18 複製程式碼
變數
很多時候restful api的uri的路徑中包含資料庫自增長的ID, 其可能是一個非同步操作生成,導致我們不能直接從API返回結果中拿到,只能從資料庫中根據測試資料的條件查詢,並在後續API測試中使用,使用pandaria我們可以這麼寫:
* query: """ select id from users where name='test-user-name'; """ * var: 'auto_generated_id'<-'$[0].id' * uri: /users/${auto_generated_id} * send: GET * verify: '$.id'=${auto_generated_id} * verify: '$.name'='test-user-name' 複製程式碼
上述程式碼首先從資料庫查出自增長的id
,然後使用<-
操作符將結果中的id
定義為名為auto_generated_id
的變數,並在後續的操作中使用這個變數。