公司主要業務包含游戲AI及自動化測試,我們的AI團隊需要利用移動設備對游戲內AI機器人的表現做一些持續性跟蹤優化,自動化測試團隊這邊對于游戲的UI自動化測試開發工作也在不斷向前推進,兩者對于移動設備的使用都是必要的。
由于移動設備資源有限,存在頻繁互借,忘記歸還等情況。為了解決管理和調用問題,我們做了一些深入調研,最后了解到,可以采用開源框架STF或者是ATXServer2來解決,將有限的資源達到最大化的輸出。下面會對通過這兩種方式搭建移動設備管理平臺做個簡單的介紹,同時,也做個簡單的比較,大家可以根據公司業務情況對其進行選擇。
1. 基于STF搭建移動設備管理平臺
1.1 STF介紹及優劣勢分析
- STF是最早的遠程真機調試平臺,現在所有的遠程真機調試其實都是借鑒了它的實現思想。
- 優勢:支持Android/ target=_blank class=infotextkey>安卓2.3-10.0系統(10.0系統為目前最新)通過瀏覽器遠程控制,支持遠程鼠標鍵盤對真機進行操作遠程復制粘貼功能快照截圖應用包及文件的上傳/下載功能支持遠程端瀏覽器進行真機訪問操作日志輸出及錯誤日志輸出打印腳本運行(可實現后續的自動化測試)開發人員進行遠程debug功能提供設備機的CPU,內存,電量等性能的監測固化測試機器的系統版本,系統設置,不被篡改
- 劣勢:僅支持安卓手機遠程控制,IOS不支持(需要二次開發)并不能很好兼容國內各種各樣的安卓定制化手機,可能會遇到STF.APK無法正常安裝到手機或者無法正常自動啟動服務的情況。
1.2 架構介紹(Nodejs+Angularjs+Rethinkdb)
STF的核心功能可以理解為:“同步圖像” + “點擊”。前者使用minicap完成,后者依賴minitouch。
具體結構看下圖:
設備端
- STF在會在android設備上安裝minicap和minitouch。使用minicap來捕獲屏幕,使用minitouch來觸發多點觸控事件,并通過adb使用socket在服務端和設備端進行數據傳輸。
- STF還會在android設備上安裝STFService.apk,它在設備后臺運行,提供了一組socket api可以用來監控和執行不同的action。 同理,它也是通過adb和服務端通信,不過它使用的是protocal buffer數據格式。
- minirev,直接從Android設備的端口轉發本地服務,即便不在一個網段。
服務端
- STF的服務端由多個不同的獨立的,基于nodejs的微服務組成,這些服務之間是通過ZeroMQ通信。服務端可以進一步分成Provider 層和Application層。
Provider 層
- Provider層(stf-provider)主要負責和設備之間進行通信。
- 通過adb來監控設備狀態,當有新的設備連接,或者有設備斷開則會立刻監控到。
- 如果是新的connect設備,則provider會folck一個新的nodejs進程(stf-device), 這個進程主要負責與該設備的所有通信。
- stf由兩個部分組成,分別是stf-provider和adb。
- 需要注意的是,provider層的服務需要跑在物理機上,所有的設備需要連著這臺物理機。
Application 層
- Application層則是由stf -api、stf -app和stf -auth等微服務組成,這些微服務組成了一個完整的STF。
- 從部署的角度來看,這些服務可以跑在任意地方,唯一的要求就是,這些服務能夠通過網絡和provider通信,這也就是意味著他們需要在同一個網段上。
Client 層
- 使用Angular JS實現
- 通過websocket與服務進行通信
1.3 環境搭建
強烈建議在centos下利用Docker搭建,相信我,這絕對是最優且最簡單的方式。
(1)安裝docker服務
- 進入docker官網下載對應docker安裝包進行安裝
- 命令行執行docker version檢查是否安裝成功
(2)利用docker拉取鏡像文件
- 開啟docker服務
- 拉取docker鏡像文件
docker pull devicefarmer/stf:latest
docker pull sorccu/adb:latest
docker pull rethinkdb:latest
docker pull openstf/ambassador:latest
docker pull Nginx:latest
- 通過docker images查看鏡像文件是否拉取成功
(3) 啟動容器
- 先啟動一個數據庫
docker run -d --name rethinkdb -v /srv/rethinkdb:/data --net host rethinkdb rethinkdb --bind all --cache-size 8192 --http-port 8090
- 再啟動adb service
docker run -d --name adbd --privileged -v /dev/bus/usb:/dev/bus/usb --net host sorccu/adb:latest
- 最后啟動stf
docker run -d --name stf --net host openstf/stf stf local --public-ip 宿主機IP地址
一定要注意啟動順序,stf 依賴 rethinkdb,所以要先啟動 rethinkdb,啟動完成后使用: docker ps -a 查看是否啟動成功,順便獲取stf的container ID。
(4) 啟動STF程序
- 首先進入stf鏡像目錄
docker exec -it stf的containerID /bin/sh
- 啟動stf命令
stf local --public-ip 宿主機IP地址 --allow-remote
啟動之后,局域網瀏覽器輸入 http://宿主機IP地址:7100 可以打開STF登錄界面,隨意輸入帳號郵箱后登錄,不過目前還沒有設備。
(5) 連接設備
由于是在Centos虛擬環境搭建的平臺,不能進行設備直連,故在局域網windows電腦連接設備進行遠程連接,在未安裝STF 的電腦上暴露adb端口(搭建SDK環境),建議采用默認端口:5037;
指定端口號與服務器進行通訊:
adb -a -P 5037 fork-server server
如果出現以下錯誤:
在任務管理器中關掉 adb.exe,或使用命令 adb kill-server 關掉adb程序,重新運行上述命令。若還是執行失敗,建議換成低版本adb(1.0.32版本)再試試。
直到執行命令出現OK。
(6)切換到Centos環境連接windows下移動設備
在啟動STF的命令行輸入:
stf provider --name localhost.localdomain --min-port 7400 --max-port 7700 --connect-sub tcp://127.0.0.1:7114 --connect-push tcp://127.0.0.1:7116 --group-timeout 900 --public-ip 宿主機IP地址 --storage-url http://localhost:7100/ --adb-host 局域網windowsIP地址 --adb-port 5037 --vnc-initial-size 600x800 --mute-master never --allow-remote
連接成功后顯示移動設備信息:
STF設備列表界面:
STF設備操作界面:
1.4 過程中可能用到的一些命令
docker
docker start 容器名 #啟動某個容器
docker stop 容器名 #停止某個容器
docker rm 容器名 #刪除某個容器
linux
netstat -anp |grep 端口號 #查看端口占用
kill -9 對應端口PID #刪除進程
2. 基于ATXServer2搭建移動設備管理平臺
2.1 ATXServer2基本介紹
ATXServer2其實是在STF基礎上,使用Python3+NodeJS+rethinkdb搭建的一個設備管理平臺,功能和STF差不多,但是可以實現IOS設備遠程控制。
2.2 ATXServer2遠程控制原理簡介
Android的遠程控制主要還是基于 minicap+minitouch+atx-agent;
IOS的遠程控制主要還是基于appium fork的WebDriverAgent,因為appium在WDA中增加了MJPEG Server,所以讓遠程投屏成為了可能。(不過只支持iOS 12.0以上)
2.3 ATXServer2整體項目結構
整體項目主要包括四部分:
- rethinkdb: 一個開源的輕量級的數據庫,是用來存儲數據的。rethinkdb官網地址
- atxserver2 :這一部分主要負責處理數據,顯示與用戶的前端交互等等,所以單獨運行atxserver2也可以看到效果,當運行起來以候訪問: IP:4000 就可以看到web界面。
- atxserver2-android-provider: 這一部分是接入安卓設備必須啟動的項目,主要負責安卓設備和平臺的交互工作,要想接入安卓設備必須啟動此項目。
- atxserver2-ios-provider: 這一部分是接入IOS設備必須啟動的項目,主要負責IOS設備和平臺的交互工作,同樣的要想接入IOS設備必須啟動此項目。(注意需要mac電腦)
項目結構:
|-- static 靜態目錄
|-- temlates 前端界面
|-- web 網頁代碼
|-- urls.py 路由整合文件
|-- settings.py 配置文件
|-- database.py 數據庫操作相關
|-- utils.py 常用配置
|--views 每個界面的邏輯
|--slave.py 與atxslave通信用
|--devices.py 設備相關路由
|--base.py 基于ReguestHandler的基類
還有其他一些文件夾:
- scripts文件夾: 主要放著一些用于調試開發的工具類等,比如想調試安卓項目可以單獨運行fake_android_provider.py 與atxserver2-android-provider,并且其中的參數要改一些,一般不用太關注這個文件夾。
- examples文件夾 : 存放著一個自動化的Demo,采用的自動化框架是uiautomator2,設備占用接口參考了openstf的API。
所有的接口采用token認證,每個請求在 Header中增加 Authorization: Bearer xxxxx-token-xxxx,這個token值可以在個人的用戶信息界面獲取到,也存儲在rethinkdb里; 接口都是通過web請求調用,可以用 “httpie” 這個工具或者直接用python的 request 方法調用。
2.4 環境搭建(這里介紹手動部署方式)
(1)安裝運行rethinkdb數據庫
- rethinkdb下載安裝地址 https://rethinkdb.com/docs/install
- 最簡單的方式,跟STF搭建方法一樣,拉取docker鏡像文件,先啟動一個rethinkdb數據庫,可返回上面查看步驟。
(2)克隆代碼到本地
- 先將代碼clone到本地
git clone https://github.com/openatx/atxserver2.git
- 安裝依賴,到根目錄執行
pip3 install -r requirements.txt
(3)啟動
- 啟動atxserver服務,進入atx2所在目錄并執行
python3 main.py
- 設置監聽端口
python3 main.py --port 4000 # 默認監聽的就是這個地址
啟動之后,局域網瀏覽器打開:http://宿主機IP地址:4000, 完成認證之后就可以順利的看到設備列表頁了。不過目前還是空的,什么都沒有。
(4)Android設備接入
接下來,進行安卓設備接入。這時需要用到另外一個項目 atxserver2-android-provider 這個項目運行需要Python3.6+和NodeJS(官網強調node必須使用node8);
- 先將代碼clone到本地,我是clone到了同局域網windows設備上,考慮可以連接移動設備。
git clone https://github.com/openatx/atxserver2-android-provider.git
- 安裝依賴,到atxserver2-android-provider根目錄執行
pip3 install -r requirements.txt
- 檢查移動設備連接
adb devices
- 啟動Provider服務連接宿主機,進入到atxserver2-android-provider根目錄執行
python main.py --server 宿主機IP地址:4000
Provider可以通過adb track-devices自動發現已經接入的設備,當手機接入到電腦上時,會自動給手機安裝minicap,minitouch,atx-agent,app-uiautomator-[test].apk,whatsinput-apk。
瀏覽器輸入 宿主機IP地址:4000 訪問ATX server2設備管理系統,設備列表展示如下:
ATX server2設備管理系統設備控制界面:
3. 總結
STF主要采用的是JAVA,項目較老,更新維護稍慢,作者位于國外,交流不便;主要語言js居多,框架比較完善定型了,另外,不支持蘋果設備遠程連接;
ATXserver2主要使用python3,國內在作者,方便溝通交流;atxserver2更像是一個內核發動機,可以自己diy一些想要的功能,并且支持蘋果設備遠程連接;
基于對STF與ATXserver2的比較,我們最終選擇在ATXserver2的基礎上二次開發,加入一些想要實現的功能。當然,除了在前人種的樹下乘涼以外,我們更要追求一些新的突破!期待有想法的朋友加入,一起創新!