初識 iOS 自動化測試框架 WebDriverAgent
微信跳一跳最近很火,外掛代練什麽的也越來越多。作為一只程序猿,對外掛的原理產生了強烈的好奇心,於是埋頭研究了一階段,註意到了 WebDriverAgent 這套 Facebook 出品的自動化測試框架。
為了讓大家產生興趣,先從跳一跳外掛的實現說起。
準備工作
安裝 homebrew
homebrew 是 Mac OS 下最優秀的包管理工具,沒有之一。
xcode-select --install
ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"
安裝 python(本例中的外掛程序使用 python3)
腳本語言 python 用來編寫模擬的用戶操作。
brew install python3
安裝 libimobiledevice
libimobiledevice 是一個使用原生協議與蘋果iOS設備進行通信的庫。通過這個庫我們的 Mac OS 能夠輕松獲得 iOS 設備的信息。
brew install --HEAD libimobiledevice
使用方法:
# 查看 iOS 設備日誌
idevicesyslog
# 查看鏈接設備的UDID
idevice_id --list
# 查看設備信息
ideviceinfo
# 獲取設備時間
idevicedate
# 獲取設備名稱
idevicename
# 端口轉發
iproxy XXXX YYYY
# 屏幕截圖
idevicescreenshot
安裝 Carthage
Carthage 是一款iOS項目依賴管理工具,與 Cocoapods 有著相似的功能,可以幫助你方便的管理三方依賴。它會把三方依賴編譯成 framework,以 framework 的形式將三方依賴加入到項目中進行使用和管理。
WebDriverAgent 本身使用了 Carthage 管理項目依賴,因此需要提前安裝 Carthage。
brew install carthage
安裝 WebDriverAgent
WebDriverAgent 是 Facebook 推出的一款 iOS 移動測試框架,能夠支持模擬器以及真機。
WebDriverAgent 在 iOS 端實現了一個 WebDriver server ,借助這個 server 我們可以遠程控制 iOS 設備。你可以啟動、殺死應用,點擊、滾動視圖,或者確定頁面展示是否正確。
從 github 克隆 WebDriverAgent 的源碼。
git clone https://github.com/facebook/WebDriverAgent.git
運行初始化腳本,確保之前已經安裝過 Carthage。
cd WebDriverAgent
./Scripts/bootstrap.sh
腳本完成後可以打開工程文件,根據自己的開發者證書對 bundleid、證書等信息做下配置。
運行 WebDriverAgent
運行 WebDriverAgent 相當於在你的目標設備啟動了一個服務器,它接收來自 WDA 客戶端(一般是你的電腦)的腳本請求並執行,實現啟動、殺死應用,點擊、滾動視圖等操作。
運行 WebDriverAgent 有兩種方式,一種是打開 Xcode 運行,一種是使用腳本運行。
打開 Xcode 運行
菜單欄選擇目標設備:
選擇目標設備Scheme 選擇 WebDriverAgentRunner:
選擇 WebDriverAgentRunner最後運行 Product -> Test:
運行Product -> Test一切正常的話,手機/模擬器上會出現一個無圖標的 WebDriverAgent 應用,啟動之後,馬上又返回到桌面。這很正常不要奇怪。
此時控制臺界面可以看到設備的 IP 地址:
設備的 IP 地址通過上面給出的 IP地址 和端口,加上/status合成一個url地址。例如 http://192.168.1.104:8100/status,然後瀏覽器打開。如果出現一串 JSON 輸出,說明 WDA 安裝成功了。
此時打開 http://192.168.1.104:8100/inspector,可以看到一個酷炫的界面。左邊屏幕圖像,右邊具體的元素信息,用來查看界面都 UI 圖層,方便寫測試腳本用。
Inspector腳本運行(推薦)
# 解鎖keychain,以便可以正常的簽名應用,
PASSWORD="YourPassword"
security unlock-keychain -p $PASSWORD ~/Library/Keychains/login.keychain
# 獲取設備的UDID,用到了之前的 libimobiledevice
UDID=$(idevice_id -l | head -n1)
# 真機運行測試
xcodebuild -project WebDriverAgent.xcodeproj -scheme WebDriverAgentRunner -destination "id=$UDID" test
# 模擬器運行測試
#xcodebuild -project WebDriverAgent.xcodeproj -scheme WebDriverAgentRunner -destination "platform=iOS Simulator,name=iPhone X" test
腳本運行完成後,同樣手機/模擬器上會出現一個無圖標的 WebDriverAgent 應用,啟動之後,馬上又返回到桌面。此時終端會輸出 IP 地址和端口。
端口轉發
有些國產的iPhone機器通過手機的IP和端口還不能訪問,此時需要將手機的端口轉發到Mac上。需要用到之前安裝的 libimobiledevice 這個庫。
# 把當前連接的 iOS 設備端口轉發到 MacOS 的端口
iproxy 8100 8100
完成後可以直接使用 http://localhost:8100/status 查看是否返回 JSON。inspector 也可以使用 http://localhost:8100/inspector 訪問。
安裝 WDA 客戶端
上面我們在 iOS 設備上啟動了 WDA 的服務端。為了運行 Mac OS 上的腳本,我們需要在 Mac OS 上安裝 WDA 客戶端。
facebook-wda 就是 WDA 的 Python 客戶端庫,通過直接構造HTTP請求直接跟WebDriverAgent通信。
安裝 WDA python 客戶端,可以上官網下載安裝,但推薦使用pip安裝。
# 安裝 WDA python 客戶端,微信跳一跳是 python3 編寫,因此使用 pip3 安裝
pip3 install --pre facebook-wda
運行客戶端外掛腳本
WDA python 客戶端安裝完畢後,就剩腳本代碼了。不要急,github 上有現成的外掛程序代碼。
# 克隆代碼
git clone https://github.com/wangshub/wechat_jump_game.git
安裝外掛腳本需要的依賴:
pip install -r requirements.txt
config 目錄下有許多配置文件,裏面是程序運行時,與手機截圖像素相關的一些全局參數,腳本作者很貼心的把所有適配的手機像素的配置參數都配好了,我們只需要找到我們手機對應的json配置文件,復制到腳本工程的根目錄下的並且命名為 config.json 文件就可以了。
打開微信跳一跳小程序,點擊“開始遊戲”。
執行腳本:
python3 wechat_jump_auto_iOS.py
好了,現在坐等高分就可以了。
自動跳躍感興趣的同學可以自己翻看一下源碼,基本原理是利用截圖分析距離然後算出點擊時長。
下一次運行
以後每次需要運行的時候,只需要按順序運行下列命令即可。一共要打開三個終端。
1.在iOS設備上啟動 WDA 服務器,推薦直接寫在一個 shell 文件裏。
# 解鎖keychain,以便可以正常的簽名應用,
PASSWORD="YourPassword"
security unlock-keychain -p $PASSWORD ~/Library/Keychains/login.keychain
# 獲取設備的UDID,用到了之前的 libimobiledevice
UDID=$(idevice_id -l | head -n1)
# 真機運行測試
xcodebuild -project WebDriverAgent.xcodeproj -scheme WebDriverAgentRunner -destination "id=$UDID" test
# 模擬器運行測試
#xcodebuild -project WebDriverAgent.xcodeproj -scheme WebDriverAgentRunner -destination "platform=iOS Simulator,name=iPhone X" test
2.配置手機端口轉發。
iproxy 8100 8100
3.運行 WDA 客戶端腳本
python3 wechat_jump_auto_iOS.py
以上步驟同樣適用於任何自動化測試步驟,唯一不同的地方在於將上面的微信客戶端外掛腳本改為自己寫的測試腳本。
WebDriverAgent 原理
WebDriverAgent 原理圖左側為 PC 端,右側為 iOS 端。PC 端(MacOS)運行 WebDriverAgent 工程,令 iOS 端啟動 WDA 的 App, 這個 App 實現了一個 WebDriver server。然後 PC 端(可以不是運行 WDA 工程的那臺 PC)作為客戶端運行測試用例腳本並以 http 協議向 iOS 端的 WDA App 發起請求。最後 iOS 端的 WDA App 接受請求並且啟動被測 App 執行測試用例。
需要註意的是,整個過程的服務端和客戶端與我們平常理解的完全相反。這裏 iOS 端是作為服務端,而運行測試腳本的 PC 端反而是發起請求的客戶端。
自動化測試開發
原理理解清楚了,那就讓我們開始寫一些自動化測試的相關代碼吧。
設備連接和彈窗處理
App 可能彈出一些彈框,比如通知、相機的權限請求,或者是 App 給用戶的某些提示,總體上來講,這些彈框的出現無法預估。因此需要對於彈框進行統一處理。
# -*- coding: utf-8 -*-
import wda
import time
bundle_id = ‘your_app_bundle_id_here‘
c = wda.Client(‘http://localhost:8100‘)
s = c.session(bundle_id)
def alert_callback(session):
btns = set([u‘不再提醒‘, ‘OK‘, u‘知道了‘, ‘Allow‘, u‘允許‘]).intersection(session.alert.buttons())
if len(btns) == 0:
raise RuntimeError("Alert can not handled, buttons: " + ‘, ‘.join(session.alert.buttons()))
session.alert.click(list(btns)[0])
s.set_alert_callback(alert_callback)
控件定位
如何模仿用戶操作,點擊一個按鈕呢?還記得之前介紹的 inspector 麽?通過訪問 http://localhost:8100/inspector 可以獲取應用的UI圖層結構,方便我們定位控件,寫測試腳本模擬用戶點擊。
定位控件# 點擊酒店按鈕
s(name=u‘酒店‘).tap()
斷言
自動化測試最重要的就是斷言。斷言雖然不能像人工判斷預期結果那樣準確,但合理靈活地運用,對於重要節點加上斷言也是具有一定判斷預期的效果的。
加入斷言後的一個較完整的測試用例:
def test_index(s):
# 首頁廣告停頓幾秒
time.sleep(3)
# 點擊酒店項目
s(name=u‘酒店‘).tap()
assert s(name=u‘搜索‘, type=‘Button‘).wait(3.0)
# 返回按鈕
s.tap(20,55)
test_index(s)
寫在最後
WebDriverAgent 本身功能非常完善,能做自動化測試,能寫 App/小程序 外掛,本文只是引了個路,小試牛刀,拋磚引玉,具體如何去使用它,需要大家自己深入挖掘。
小禮物走一走,來簡書關註我
贊賞支持 日記本 ? 著作權歸作者所有 舉報文章 關註 ReinhardHuang寫了 14023 字,被 40 人關註,獲得了 55 個喜歡
大概算是個iOS開發者,人工智能關註者,沒時間玩遊戲的硬核遊戲迷,從ACG發展而來的業余人文學家。作者:ReinhardHuang
鏈接:https://www.jianshu.com/p/d64c901e56c7
來源:簡書
簡書著作權歸作者所有,任何形式的轉載都請聯系作者獲得授權並註明出處。
初識 iOS 自動化測試框架 WebDriverAgent