AppCrawler自動化遍歷使用詳解(版本2.1.0 )
阿新 • • 發佈:2017-09-22
穩定 second 而是 assert 重新 app awl 好用 國內 AppCrawle是自動遍歷的app爬蟲工具,最大的特點是靈活性,實現:對整個APP的所有可點擊元素進行遍歷點擊。
優點:
1.支持android和iOS, 支持真機和模擬器
2.可通過配置來設定遍歷的規則(比如設置黑名單和白名單,提高遍歷的覆蓋率)
3. 其本身的遍歷深度覆蓋較全,比如它擁有APP的dom樹,根據每個activity下的可點擊元素逐個點擊,比monkey更具有規律性,覆蓋更全面
4.生成的報告附帶截圖,可以精確看到點擊了哪個元素及結果,對crash類的問題定位清晰
缺點:
1. 只能定位一頁,對於翻頁的無法進行下滑再點擊,導致下面的內容無法遍歷(需要自己設置下滑然後翻頁)
2.對於調用第三方應用的不太穩定,比如每次到上傳頭像處就停止遍歷
3.對於 整個layout區域是可點擊,但是其中某個元素是不可點擊的,沒有進行遍歷點擊,比如:左上角的設置和右上角的私信都不能遍歷到
4.對於H5頁面無法進行精確的定位點擊,比如它的整個布局layout是 一個大模塊,不能進行點擊 (機會頁,融資速遞,新品優選)
一.環境搭建:(前提是當然得有Java環境)
1.appcrawler的最新jar包(最新的功能多,兼容性比較高),我用的是 appcrawler-2.1.0.jar ,
下載地址如下:
百度網盤: https://pan.baidu.com/s/1bpmR3eJ
2. appium ,用來開啟session服務並定位元素的,也可以使用 appium GUI(桌面版),但是我使用跑了一半就崩潰了,內存不足,所以推薦使用命令行版本的
下載方式:
(1)在命令行下執行npm --registry http://registry.cnpmjs.org install -g appium (推薦這種,npm的國內鏡像)
(2)檢查appium所需的環境是否OK(這步很重要):進入Cmd命令行,輸入appium-doctor 顯示正常則成功
3.Android SDK,主要是為了使用tools文件夾下的 uiautomatorviewer.bat 來定位元素,獲取元素的xpath,用於準備工作前期。
二.執行步驟:
1.手機安裝好最新的安裝包,不需要登陸(避免不能遍歷登陸前的頁面內容,且登錄後再進行遍歷會出現activity不一致的報錯,即和launchActivity不一致)
2.開啟appium服務
在命令行中輸入: appium ,提示: 則開啟成功
3.在放 appcrawler-2.1.0.jar 的文件夾下執行以下命令:
Java -jar appcrawler-2.1.0.jar -a jingdata.apk -c config.yml --output wyy/
即可自動啟動APP,並自動遍歷點擊元素
因為遍歷的深度比較大,在覆蓋比較全面的條件下,我這邊測試會有496條case左右,基本要跑1個小時左右。
最後自動生成的報告如下:
三. 如何寫配置文件 config.yml (這才是運行的核心所在)
參數說明:
Java -jar appcrawler-2.1.0.jar 用來啟動appcrawler
-a 後面跟安裝包的名字 (用於自己手機沒有安裝包的時候的使用)
-c 後面跟自定義的配置文件的路徑和名字
-output 後面跟輸出的報告所在的文件夾,如果沒有寫,則會自動生成一個以時間為文件夾名字的報告文件
其實這裏的重點就是如何來寫配置文件:
配置文件基本都是以key-value格式,所以可以用文本編輯器,然後改名為 .yml或者.json文件即可。
先上一下我的配置文件 config.yml:
---
logLevel: "TRACE"
reportTitle: "Jingdata" #指生成的HTML(index.html)報告頭部顯示的標題信息
saveScreen: true
screenshotTimeout: 20
currentDriver: "android"
showCancel: true
tagLimitMax: 5
tagLimit:
- xpath: //*[../*[@selected=‘true‘]]
count: 12
maxTime: 10800
resultDir: "" #結果文件夾名,給定後,將不動態命名
capability:
newCommandTimeout: 120
launchTimeout: 120000
platformVersion: ""
platformName: "Android"
autoWebview: "false"
autoLaunch: "true"
noReset: "true"
androidInstallTimeout: 180000
androidCapability:
deviceName: ""
appPackage: "com.android36kr.investment"
appActivity: "" #寫不寫無所謂,因為APP會自動判別當前的activity是否正確,是不是launchActivity,如果不是則會報錯
dontStopAppOnReset: true
app: ""
appium: "http://127.0.0.1:4723/wd/hub"
# automationName: uiautomator2
automationName: uiautomator2
reuse: 3
headFirst: true
enterWebView: true
urlBlackList:
- //*[contains(@resource-id, "tv_setting_logout") and @clickable=‘true‘] #登出
- //*[contains(@resource-id, "toolbar_close") and @clickable=‘true‘] # 關閉按鈕,否則會陷入死循環一直遍歷同一個頁面
- //*[contains(@resource-id, "login_36kr_forgot_pass") and @clickable=‘true‘] # 忘記密碼,避免登陸時按照遍歷順序影響登陸
- //*[contains(@resource-id, "mine_info_icon") and @clickable=‘true] # 我的資料 頭像部分設置不可點擊(每次一運行到這裏就結束了)
- //*[contains(@resource-id, "tv_name") and @clickable=‘true] #頭部卡片 姓名
- //*[contains(@resource-id, "tv_company_name") and @clickable=‘true] # 頭部卡片 公司和職位
- //*[contains(@resource-id, "company_avatar") and @clickable=‘true] # 頭部 禁止進入我的資料頁面
- //*[contains(@resource-id, "chat_invest_card_rl") and @clickable=‘true] # 聊天頁的項目頭部,避免又進入詳情頁,跳出了循環
- //*[contains(@resource-id, "chat_send_contact_ll") and @clickable=‘true] #聊天詳情頁,交換名片,避免遍歷線上包時與線上用戶交互
- //*[contains(@resource-id, "ll_header") and @clickable=‘true] # 我的資料頭像部分的整個頭部區域,因為一點擊頭像後喚起照相就不運行了
urlWhiteList:
- //*[contains(@resource-id, "login_36kr_ll") and @clickable=‘true‘] #必須遍歷賬號密碼登錄的按鈕(以此方式才能登錄成功)
- //*[contains(@resource-id, "fl_msg") and @clickable=‘true‘] #右上角的私信按鈕
- //*[contains(@resource-id, "iv_setting") and @clickable=‘true‘] # 左上角的設置按鈕
backButton:
- //*[contains(@resource-id, "toolbar_back") and @clickable=‘true‘]
triggerActions: # 主要解決登錄的問題,當遇到登錄輸入框時,輸入內容,比testcase更好用
- action: "1771019****"
xpath: "//*[@resource-id=‘com.android36kr.investment:id/login_36kr_phone_edit‘]"
times: 1
- action: "123456"
xpath: "//*[@resource-id=‘com.android36kr.investment:id/login_36kr_pass_code‘]"
times: 1
- action: "click"
xpath: "//*[@resource-id=‘com.android36kr.investment:id/login_36kr_go_btn‘]"
times: 1
- action: "swipe("down")"
xpath: "//*[@resource-id=‘com.android36kr.investment:id/share‘]"
times: 1
startupActions:
- swipe("left")
- println(driver)
testcase:
name: swipeTest
steps:
- when:
xpath: //*[contains(@resource-id, ‘share‘)]
action: driver.swipe(0.5,0.8,0.5,0.2)
then: []
還有一些其他的參數說明如下:
1、java -jar appcrawler-2.1.0.jar --capability appPackage=xxxxxx,appActivity=xxxxxx
2、appium --session-override:4:10,配置文件說明:11:00(看視頻主要地方)
3、配置文件使用:true和false是開啟和關閉的意思
logLevel:日誌級別
saveScreen:是否截圖
reportTitle:報告名字
screenshotTimeout:屏幕超時時間
currentDriver:當前設備(Android/iOS)
resultDir:結果文件夾名,給定後,將不動態命名
tagLimitMax:ios的元素tag控制
tagLimit:給tag
maxTime:最大運行時間
showCancel:應該是控制是否展示註釋
capability:用於配置appium
androidCapability:Android專屬配置,最後會和capability合並
iosCapability:iOS專屬配置
urlWhiteList/blackList:白名單/黑名單
xpathAttributes:用來設定可以用那些種類型去定位控件
defineUrl:用來確定url的元素定位xpath 他的text會被取出當作url因素(沒理解)
baseUrl:設置一個起始url和maxDepth, 用來在遍歷時候指定初始狀態和遍歷深度
maxDepth:默認的最大深度10, 結合baseUrl可很好的控制遍歷的範圍
appWhiteList:app白名單,如果跳轉到其他app,需要設定規則,是否允許停留在次app中
headFirst:是否是前向遍歷或者後向遍歷
enterWebView:是否遍歷WebView控件
urlBlackList:url黑名單.用於排除某些頁面
urlWhiteList:url白名單, 第一次進入了白名單的範圍, 就始終在白名單中. 不然就算不在白名單中也得遍歷.
上層是白名單, 當前不是白名單才需要返回
defaultBackAction:默認的返回動作(沒看到例子,貌似不特指的話,是click)
backButton:給一些返回控件,用於返回動作使用
firstList:優先遍歷元素
selectedList:默認遍歷列表,如果不是指定的類型,而是確定控件,會分別點擊控件
lastList:最後遍歷的元素
blackList:排除某些控件
triggerActions:制定規則(action、xpath、times)
autoCrawl:自動抓取,看源碼指定true後運行crawl(conf.maxDepth)命令
(crawl——清空堆棧 開始重新計數)應該是appcrawler的主要方法
asserts:斷言,用於是否失敗的判斷
testcase:測試用例,看appcrawler日誌,每次都是首先運行用例才會往下執行
beforeElementAction:貌似沒什麽人用,字面意思在元素動作之前
afterElementAction:與beforeElementAction的待遇差不多
afterUrlFinished:也是很冷門的待遇
monkeyEvents:monkey的點擊數
monkeyRunTimeSeconds:monkey運行時間
given是條件 或輸入 when是觸發條件和動作 then是斷言
4、一次ctrl+c生成報告,兩次ctrl+c是強行退出
5、終端輸入Scala進入Scala解釋器,輸入:q或:quit退出解釋器
6、遍歷的深度應該怎麽設置好,總是跳到其它頁面,就回不到當前頁面繼續遍歷了,看文檔 通過黑白名單
7、設置一個起始url和maxDepth, 用來在遍歷時候指定初始狀態和遍歷深度
四. 遇到的問題有哪些?如何解決
1.登錄: 因為APP的登錄頁面是用戶名+驗證碼,由於該頁面按鈕眾多且有驗證圖標,需要滑動解鎖很復雜,所以選用了賬號密碼登錄的方式 (1)設置 賬號密碼登錄 按鈕為白名單,即必須點擊,此時一定會編輯進入賬戶名密碼登錄頁面,配置如下: urlWhiteList: - //*[contains(@resource-id, "login_36kr_ll") and @clickable=‘true‘] #必須遍歷賬號密碼登錄的按鈕 (2)設置賬號密碼登錄中,用戶名和密碼元素的觸發器,當定位到這兩個元素時,輸入用戶名和密碼,配置如下: triggerActions: # 主要解決登錄的問題,當遇到登錄輸入框時,輸入內容,比testcase更好用 - action: "177*******" xpath: "//*[@resource-id=‘com.android36kr.investment:id/login_36kr_phone_edit‘]" times: 1 - action: "123456" xpath: "//*[@resource-id=‘com.android36kr.investment:id/login_36kr_pass_code‘]" times: 1 (3)設置賬號密碼登錄中,輸入用戶名和密碼後,按照遍歷順序,接下來有一個忘記密碼的點擊事件開啟了新頁面,為了避免登陸的多余操作,將 忘記密碼 這個元素設置為黑名單,不進行遍歷,配置如下: urlBlackList: - //*[contains(@resource-id, "login_36kr_forgot_pass") and @clickable=‘true‘] # 忘記密碼,避免登陸時按照遍歷順序影響登陸 2. 聊天詳情頁 因為是線上包,為了避免點擊交換名片,直接發送聯系方式給線上用戶,所以 將 交換名片的按鈕設置 為 黑名單 3.聊天詳情頁 聊天詳情頁的項目卡片點擊後重新進入到項目頁面,導致重復遍歷,所以將項目卡片的可點擊元素設置為 黑名單 4.頭像部分 點擊頭像會調起相機,導致運行到此處就 shutdown ,所以設置所有可點擊的頭像部分都為 黑名單,運行就正常了。 yeah~ 搞定,over~~ 開心 O(∩_∩)O~~AppCrawler自動化遍歷使用詳解(版本2.1.0 )