1. 程式人生 > >Appium python自動化測試系列之認識Appium(四)

Appium python自動化測試系列之認識Appium(四)

ndt require 差異 make python自動化 復雜 appium launched interface

?4.1界面認識

在之前安裝appium的時候說過我們有兩種方法安裝,也就有兩種結果,一種是有界面的,一種是沒有界面的,首先我們先講一下有界面的,以及界面有哪些東西。

首先看第一幅圖,如果你的是windows那麽界面就應該是這樣的,所以你發現你的和我的不一樣也不用擔心,正常。windows版整個界面只有7個按鈕,我會按照從左到右從上到下的順序講。(mac的會有一定的差異,但並不是很大,只是排版和樣式的問題,但是功能都一樣。)

技術分享

Android Settings:左邊的第一個按鈕,主要是配置android的相關設置,他裏面的結構圖我們看下張圖片

技術分享

Application Path:選擇路徑,選擇需要測試的app在本電腦存放的一個路徑。在啟動appium時他會默認去該路徑下去尋找這個app,然後將他安裝到指定的手機上。

Package:之前提到過的,我們這個包的身份證,我們需要通過這個去找到包,不然我們安裝後我們通過什麽去辨別這些包呢?

Launch Activity:故名思義,啟動的activity,activity的時候提到過,我們啟動app時需要去運行的activity,這裏我們填寫首次啟動頁面的activity。

備註:這裏需要註意一個問題在我們每次通過Choose選擇apk後,appium會自動把這個包進行重新簽名,那麽在package以及activity裏面會自動把包名和activity的名稱列進去,但是這裏會出現一個問題,每次選擇apk後列表中會有一個緩存的原因,即使你更改了apk,但是package還是沒有變,這樣啟動的時候就一直報錯,遇見這樣的情況不要著急,重新啟動兩次就好。

Wait for Activity: 和上面的差不多,意思是等待某個Activity打開,用的時間不是很多,做了解。

Launch Device:標簽下面的東西用得相對比較少,後面大家可以去了解一下。

Capabilities:該標簽下和我們做自動化關系很大,後面我們做自動化時如何配置啟動app等信息就用的該標簽下的數據。

Platform Name:我們測試的app的類型,ios選擇ios,android選擇Android就好。

Automation Name:測試引擎的名稱,我們使用的是appium,所以你第一眼就能看見Appium,但是他還有一個Selendroid。可能看到這裏會有一些疑惑,為什麽appium要選擇兩套系統呢?其實這個應該追溯到android的版本問題,android自己的工具在4.2版本以前是一個,但是後面進行了更新,可能也正是因為這個原因appium也才采用了兩套,所以當你測試的app安裝的機器時在4.0或之前的版本時那麽這裏的引擎你就必須選擇Selendroid,是否這樣大家可以動手去試一試。檢驗真理的唯一標準就是自己動手嘗試。

Platform Version:安裝應用手機的版本號,android的是幾點幾的版本。

Device Name:設備名稱。

備註:這裏會有一個問題,如果你測試android時,只把一臺手機插入到電腦,即使你輸入的Device Name是錯誤的,但是你依然能夠正常安裝,使用。但是ios是不行的。不知道在設計的時候是否就是如此考慮的,如果在以後使用中遇見類似問題大家不要驚慌。

Advanced標簽下的東西在初級階段不用擔心,這個標簽只是在你想同一臺電腦同時控制多臺手機的時候才能使用,需要更改Bootstrap Port的端口號,記住這一點就好。

General Setting:

在General Setting裏面在通常情況下我們使用默認設置就好,但還是有一些基礎設置可以進行調整,方便後期的學習。整個頁面分成了Server和log兩部分,默認的情況如下面圖片。

技術分享

Server Address:配置appium服務的地址,正常情況我們不需要更改,但是如果我們需要配置多臺手機的時候啟動了多個appium服務,那麽這裏的端口號我們需要進行調整,如果你多個都弄的同一個端口會報錯。

Override Existing Session:session覆蓋,可能對於初學者不理解什麽叫session,你這裏暫時理解為會話,我和你會話的唯一標示。

Log To File:默認狀態是沒有任何數據,但是在做自動化時建議選擇,因為選擇之後appium在運行時產生的日誌都會保留到你設置的問題件,這個對後期的bug定位有相當大的幫助。切記!

開發者設置(左邊第三個按鈕)很少用,可以忽略。如果有興趣可以作為興趣了解一下。

關於(左邊第四個按鈕),查看當前appium的版本信息。

元素偵測(右邊第二個按鈕):這個按鈕的功能和firebug的定位工具功能類似,但是他還有一個功能,他會檢測你的各個系統配置是否正確,如果前面各項參數不正確時,使用該功能會報錯。如果你不正常連接手機也不行。還是建議用sdk工具裏面自帶的uiautomatorviewer。

啟動服務(右邊第一個按鈕):所有參數配置好後你需要做的就是啟動appium服務,只有啟動之後你才能夠做自動化。

清除日誌(右下角):在寫腳本、調試過程中會產生很多的日誌,但是你可能想看的只是中間某個時間段的,那麽你在這個時候可以將頁面的日誌清除。

4.2 日誌分析

通過前面的學習加上自己動手練習我相信很多小夥伴都能夠將appium啟動起來,並且會自動將app安裝到手機或者模擬器,但是這個時候很多人看見appium的面板或者控制臺會比較頭疼。appium服務頁面不斷的在滾動日誌,但是又看不懂,這個可能是通病。下面我們來分析一下這個日誌,我們下面大概來解讀一下我這個日誌,讓自己不再迷茫。在每一行的上面我來配置解讀,讓大家更容易理解。

我啟動appium服務,指定了ip、端口、以及我的uid

192:~ ytxu$ appium -a 127.0.0.1 -p 4723 -U 127.0.0.1:62001

啟動成功

[Appium] Welcome to Appium v1.6.3

[Appium] Non-default server args:

啟動成功後的服務地址

[Appium] address: ‘127.0.0.1‘

我們的uid,因為我這裏是鏈接的模擬器所以用的這個IP

[Appium] udid: ‘127.0.0.1:62001‘

[Appium] Deprecated server args:

系統自動拼接成字典的形式

[Appium] -U,--udid => --default-capabilities ‘{"udid":"127.0.0.1:62001"}‘

[Appium] Default capabilities, which will be added to each request unless overridden by desired capabilities:

[Appium] udid: ‘127.0.0.1:62001‘

REST http接口監聽的是哪個端口

[Appium] Appium REST http interface listener started on 127.0.0.1:4723

通過POST的方式創建了一個session,這個session裏面的值就是我們在配置app時的一些數據,這裏系統把他自動轉換成了字典的形式,一個key對應一個value。仔細去看你會發現都不陌生。

[HTTP] --> POST /wd/hub/session {"requiredCapabilities":{},"desiredCapabilities":{"deviceName":"127.0.0.1:62001","app":"/Users/ytxu/Desktop/AppiumPython/apps/mukewang.apk","autoLaunch":"true","platformVersion":"4.1","appPackage":"cn.com.open.mooc","platformName":"Android","appActivity":"cn.com.open.mooc.index.splash.MCSplashActivity"}}

[debug] [MJSONWP] Calling AppiumDriver.createSession() with args: [{“deviceName":"127.0.0.1:62001","app":"/Users/ytxu/Desktop/AppiumPython/apps/mukewang.apk","autoLaunch":"true","platformVersion":"4.1","appPackage":"cn.com.open.mooc","platformName":"Android","appActivity":"cn.com.open.mooc.index.splash.MCSplashActivity"},{},null,null,null]

創建一個會話,準備開始對話,把開始填寫的數據,傳入數據後用服務端驗證,如果成功就會話開始。

[Appium] Creating new AndroidDriver session

[Appium] Capabilities:

[Appium] deviceName: ‘127.0.0.1:62001‘

[Appium] app: ‘/Users/ytxu/Desktop/AppiumPython/apps/mukewang.apk‘

[Appium] autoLaunch: ‘true‘

[Appium] platformVersion: ‘4.1‘

[Appium] appPackage: ‘cn.com.open.mooc‘

[Appium] platformName: ‘Android‘

[Appium] appActivity: ‘cn.com.open.mooc.index.splash.MCSplashActivity‘

[Appium] udid: ‘127.0.0.1:62001‘

[debug] [AndroidDriver] AndroidDriver version: 1.10.38

看到這裏你是否還覺得這個很麻煩?其實只要你仔細去看你會很容易都了解的。可能這裏會有小夥伴說這個啟動的很容易,但是在實際中遇見的問題就沒這麽容易了,那麽下面我們看一個實際遇見的問題,直接看日誌:

debug] [ADB] We tried to start an activity that doesn‘t exist, retrying with . prepended to activity

[debug] [ADB] Device API level: 19

[debug] [ADB] Getting connected devices...

[debug] [ADB] 1 device(s) connected

[debug] [ADB] Running ‘/Users/ytxu/Library/Android/sdk/platform-tools/adb‘ with args: ["-P",5037,"-s","127.0.0.1:62001","shell","am","start","-W","-n","cn.com.open.mooc/.cn.com.open.mooc.aindex.splash.MCSplashActivity","-S","-a","android.intent.action.MAIN","-c","android.intent.category.LAUNCHER","-f","0x10200000"]

[ADB] Error: Activity used to start app doesn‘t exist or cannot be launched! Make sure it exists and is a launchable activity

at Object.wrappedLogger.errorAndThrow (lib/logger.js:60:13)

at ADB.callee$0$0$ (../../../lib/tools/apk-utils.js:68:13)

at tryCatch (/usr/local/lib/node_modules/appium/node_modules/babel-runtime/regenerator/runtime.js:67:40)

at GeneratorFunctionPrototype.invoke [as _invoke] (/usr/local/lib/node_modules/appium/node_modules/babel-runtime/regenerator/runtime.js:315:22)

at GeneratorFunctionPrototype.prototype.(anonymous function) [as next] (/usr/local/lib/node_modules/appium/node_modules/babel-runtime/regenerator/runtime.js:100:21)

at GeneratorFunctionPrototype.invoke (/usr/local/lib/node_modules/appium/node_modules/babel-runtime/regenerator/runtime.js:136:37)

Error: Activity used to start app doesn‘t exist or cannot be launched! Make sure it exists and is a launchable activity

at Object.wrappedLogger.errorAndThrow (lib/logger.js:60:13)

at ADB.callee$0$0$ (../../../lib/tools/apk-utils.js:68:13)

at tryCatch (/usr/local/lib/node_modules/appium/node_modules/babel-runtime/regenerator/runtime.js:67:40)

at GeneratorFunctionPrototype.invoke [as _invoke] (/usr/local/lib/node_modules/appium/node_modules/babel-runtime/regenerator/runtime.js:315:22)

at GeneratorFunctionPrototype.prototype.(anonymous function) [as next] (/usr/local/lib/node_modules/appium/node_modules/babel-runtime/regenerator/runtime.js:100:21)

at GeneratorFunctionPrototype.invoke (/usr/local/lib/node_modules/appium/node_modules/babel-runtime/regenerator/runtime.js:136:37)

[ADB] Error: Error occured while starting App. Original error: Activity used to start app doesn‘t exist or cannot be launched! Make sure it exists and is a launchable activity

at Object.wrappedLogger.errorAndThrow (lib/logger.js:60:13)

at ADB.callee$0$0$ (../../../lib/tools/apk-utils.js:80:9)

at tryCatch (/usr/local/lib/node_modules/appium/node_modules/babel-runtime/regenerator/runtime.js:67:40)

at GeneratorFunctionPrototype.invoke [as _invoke] (/usr/local/lib/node_modules/appium/node_modules/babel-runtime/regenerator/runtime.js:315:22)

at GeneratorFunctionPrototype.prototype.(anonymous function) [as next] (/usr/local/lib/node_modules/appium/node_modules/babel-runtime/regenerator/runtime.js:100:21)

at GeneratorFunctionPrototype.invoke (/usr/local/lib/node_modules/appium/node_modules/babel-runtime/regenerator/runtime.js:136:37)

Error: Error occured while starting App. Original error: Activity used to start app doesn‘t exist or cannot be launched! Make sure it exists and is a launchable activity

at Object.wrappedLogger.errorAndThrow (lib/logger.js:60:13)

從第一眼看見這個日誌我知道大家的第一反應已經暈了,沒事我們來仔細看。就日誌的第一行說的大概意思就是“我們盡力去運行這個Activity了,但是他還是不存在。”那麽看到這裏小夥伴應該思考一個問題,在前面配置頁面時就講過如果你配置package或者activity錯誤那麽是無法啟動的。現在已經告訴我們說這個Activity不存在了是否應該去仔細檢查一下呢?

其實在整個日誌中我們應該直接去看error的部分,[ADB] Error: Activity used to start app doesn‘t exist or cannot be launched! Make sure it exists and is a launchable activity,這是error的日誌,給出的提示也是這個activity不能夠被啟動,讓你再次確認後再去啟動。

從這個小小的實驗我們能夠看出日誌本身並不難,難的是我們沒仔細看。所以以後遇見問題不要煩躁,應該仔細看日誌,然後解決問題。

4.3 appium的工作原理

我們在去熟悉一套系統或者框架的時候,我們想去學好,我們是不是都要了解一下工作原理呢?只有我們知道了他是如何工作之後,在以後我們遇見棘手的問題時才能夠從根本去解決問題。但是在講這個之前需要講一個題外話,不知道有誰思考過appium是如何實現自動化的嗎?無論ios還是android在做自動化時考慮到安全等因素他們都是不允許直接去操作的,所以我們要做自動化那麽就必須借助他們本身公布出來的一些工具,android是UIAutomator,ios使用的是UIAutomation,其實我們所謂的自動化就是我們使用的工具去調用他們公布出來的框架的方法,然後再去執行。下面我們來看一下appium的工作原理,首先來看一張圖片。技術分享

通過上面的圖片我們可以知道appium是基於WebDriver協議的,他利用Bootstrap調用google公布的android的自動化測試框架UIautomator的命令來實現我們的app自動化,再能理解一點就是我們的電腦(client)上運行自動化測試腳本,調用的是webdriver的接口,appium server接收到我們client上發送過來的命令後他會將這些命令轉換為UIautomator認識的命令,然後由UIautomator來執行自動化。

可能這裏有些小夥伴會迷糊,說android是這樣那麽ios也是這樣嗎?其實真的差不多,只是他們支持的工具不一樣,ios使用的是UIAutomation,首先client發送腳本請求,再到我們的appium服務,這裏appium會調用instruments去啟動一個server,然後讓他去執行後面的操作來完成自動化。備註:UIAutomation是instruments下面的一個工具,所以不要驚慌。

4.4 Appium的優勢

現在市面上做自動化的框架無論是成熟還是一般的都有很多,我們不可能都去熟悉,但是我們需要了解一個常見的,不然你怎麽知道好與壞呢?我相信在學習自動化時就想過為什麽需要學appium,其實我在剛開始做移動自動化時選擇的是robotium,但是後來因為項目的需要發現我如果只是用robotium發現ios根本沒法做,那麽我就需要去單獨做一個,這個會很麻煩,這個時候appium剛好出來了,剛接觸他我就決定使用了,因為在之前做web自動化時用的就是selenium,所以這個用起來會很方便。下面我們來列舉一下他的優點:

1、可以同時支持android、ios

2、支持多種語言,java、python、php、Ruby等等

3、不用為復雜的環境發愁

4、如果你有selenium經驗,直接上手

從上面來看他的優點還是很多的,當然缺點也有,這裏不列舉了,免得破壞美好的印象。

當看到這裏的時候你對appium是否已經有一個模糊的影子了呢?接下來我們需要的就是去動手實戰吧。

Appium python自動化測試系列之認識Appium(四)