基于Puppteer自動化度量實踐
一、背景
1.前端自動化測試較少
前端瀏覽器眾多導致頁面兼容性問題比較多,另外界面變化比較快,一個月內可能頁面改版兩三次,這樣導致對前端自動化測試較少,大家也不是很care。18年英國的一位開發者做過一些前端測試工具調查如圖1-1所示。從圖中可以發現有43%的用戶未使用過任何前端測試工具。
圖1-1
2.基于Puppteer的自動化測試
Puppeteer(中文翻譯為“木偶”)是Google Chrome團隊官方的無界面(Headless)Chrome工具。這是一個node庫。提供高級API來控制DevTools協議無頭版Chrome。Chrome的DevTools提供了非常之多和非常方便的頁面工具,而Puppteteer則把這種能力通過Headless方式提供出來,可以在Linux操作能力,必將成為web應用的自動化測試行業標桿,場景非常之多。
3.解決實際問題
筆者是在華為DevCloud的前端團隊,團隊采用前端微服務架構,也就是說,有很多前端portal,同時每個portal有若干個前端開發進行開發維護,開發之間溝通交流較少,而且還是在異地進行開發。但每個服務同屬于DevCloud產品,所以頁面體驗、場景、控件、術語都需要保持一致,如果通過人工的方式來對每個服務頁面進行檢測是十分困難的一件工作。
Puppeteer能做什么
可以這么說,在chrome瀏覽器手動能完成的大部分事情可以使用puppteteer完成!你可以操作頁面的dom、抓取內容等等。另外puppeteer還可以:
生成頁面的截圖和PDF;
抓取SPA并生成預先呈現的內容(SSR)
從網站上抓取你所想要的內容。自動表單提交,UI測試,鍵盤輸入等等
創建一個最新的自動化測試環境,使用最新的JavaScript和瀏覽器功能,直接在最新版的chrome中運行測試。
二、Puppeteer版本
我最早使用的版本是puppetter@1.5.0版本,通過npm i pupptetter下載。里面包含自帶瀏覽器版本。如圖所示2-1所示。
圖2-1 puppeteer自帶瀏覽器
在版本1.7.0之后,google把puppeteer拆成puppteteer-core和瀏覽器兩部分。也就是說瀏覽器需要自己手動去下載。-可以通過華為云鏡像站搜索chromium進行匹配下載,如圖2-2所示。
圖2-2 puppteteer瀏覽器chrome下載
當然不同的puppeteer-core版本匹配不同的瀏覽器版本,不然會有報錯。版本匹配如圖2-3所示。大家也可以在官網github上進行查看
https://github.com/GoogleChrome/puppeteer/blob/master/docs/api.md
圖2-3 puppeteer版本匹配
三、輕松入門
這部分包括windows和linux上的配置和運行。因為最終是需要部署到linux服務上去。
1.簡單實現
如果windows下使用puppeteer非常容易,在package.json加上下面一行代碼:
"puppeteer-core":?"1.13.0",
下面是一點簡單截頻實現:
const?puppeteer?=?require('puppeteer'); (async?()?=>?{ ??const?browser?=?await?puppeteer.launch(); ??const?page?=?await?browser.newPage(); ??await?page.goto('https://example.com'); ??await?page.screenshot({path:?'example.png'}); ??await?browser.close(); })();
2.基本語法
這些是puppeteer一些基礎的語法,可以滿足一些常用功能。
async/await
看官方的例子就可以看出來,幾乎所有的操作都是異步的,如果堅持使用回調或者Promise.then 寫出來的代碼會非常丑陋且難讀,Puppeteer 官方推薦的也是使用高版本 Node 用 async/await 語法
async確保了函數返回一個promise,即使其中包含非promise。夠簡單了吧?但是不僅僅只是如此,還有另一個關鍵詞await,只能在async函數里使用,同樣,它也很cool。
關鍵詞await可以讓JavaScript進行等待,直到一個promise執行并返回它的結果,JavaScript才會繼續往下執行。
let?value?=?await?promise
查找元素
這是 UI 自動化測試最常用的功能了,Puppeteer 的處理也相當簡單
page.$(selector)
page.$(selector)
這個在底層依然是執行document.querySelector和document.querySelectorAll。但返回的不是dom對象。而是封裝的。
獲取DOM屬性
我們寫爬蟲爬取頁面圖片列表,感覺可以通過 page.$$(selector) 獲取到頁面的元素列表,然后再去轉成 DOM 對象,獲取 src,然后并不行,想做對獲取元素對應 DOM 屬性的獲取,需要用專門的 API:page.$eval(selector, pageFunction[, ...args])
Evaluate
如果我們有一些及其個性的需求,無法通過 page.$() 或者 page.$eval() 實現,可以用大招——evaluate。如下所示:
const?result?=?await?page.evaluate(()?=>?{ ?return?Promise.resolve(8?*?7); }); console.log(result);?//?prints?"56" const?aWindowHandle?=?await?page.evaluateHandle(()?=>?Promise.resolve(window)); aWindowHandle;?//?Handle???for?the?window?object.?相當于把返回對象做了一層包裹
性能
通過 page.getMetrics() 可以得到一些頁面性能數據。
Timestamp The timestamp when the metrics sample was taken.
Documents 頁面文檔數
Frames 頁面 frame 數
JSEventListeners 頁面內事件-數
Nodes 頁面 DOM 節點數
LayoutCount 頁面 layout 數
RecalcStyleCount 樣式重算數
LayoutDuration 頁面 layout 時間
RecalcStyleDuration 樣式重算時長
ScriptDuration script 時間
TaskDuration 所有瀏覽器任務時長
JSHeapUsedSize JavaScript 占用堆大小
JSHeapTotalSize JavaScript 堆總量
會返回如下數據:
{? ?Timestamp:?382305.912236, ?Documents:?5, ?Frames:?3, ?JSEventListeners:?129, ?Nodes:?8810, ?LayoutCount:?38, ?RecalcStyleCount:?56, ?LayoutDuration:?0.596341000346001, ?RecalcStyleDuration:?0.180430999898817, ?ScriptDuration:?1.24401400075294, ?TaskDuration:?2.21657899935963, ?JSHeapUsedSize:?15430816, ?JSHeapTotalSize:?23449600? }
更多功能請查看puppeteer的github官網。
https://github.com/GoogleChrome/puppeteer#usage
3.Linux安裝Puppeteer
windows下調試好的項目,在linux上運行,還是需要費一番功夫,需要配置更多的參數。如下:
(1)下載相關依賴包,這些依賴包都是chrome運行所需要的。
yum?install??pango.x86_64?libXcomposite.x86_64?libXcursor.x86_64?libXdamage.x86_64?libXext.x86_64?\? libXi.x86_64?libXtst.x86_64?cups-libs.x86_64?libXScrnSaver.x86_64?libXrandr.x86_64?GConf2.x86_64?\ alsa-lib.x86_64?atk.x86_64?gtk3.x86_64?ipa-gothic-fonts?xorg-x11-fonts-100dpi?\ xorg-x11-fonts-75dpi?xorg-x11-utils?xorg-x11-fonts-cyrillic?xorg-x11-fonts-Type1?xorg-x11-fonts-misc
(2)字體安裝:
yum?install?ipa-gothic-fonts?xorg-x11-fonts-100dpi?xorg-x11-fonts-75dpi?xorg-x11-utils?xorg-x11-fonts-cyrillic?xorg-x11-fonts-Type1?xorg-x11-fonts-misc
(3)增加—no-sandbox –disable-setuid-sandbox
const?browser?=?await?puppeteer.launch({args:['--no-sandbox',?'--disable-setuid-sandbox']})
筆者的工作環境比較復雜,中間因為權限問題導致運行報錯,這個時候需要增加一些代理設置。
四、puppeteer體驗度量實踐
前面主要是講一些puppeteer基本功能和實踐。那我們基于puppeteer怎么解決實際問題的呢。
1.規范的建立
在使用puppeteer之前,需要先梳理各微服務使用的場景,以及術語規范等,梳理清楚之后在來進行工具自動化。首先我們參照尼爾森可用性原則。
上面這位帥哥就是尼爾森(Jakob Nielsen),人機交互學博士。他通過自己的郵件列表以及網站,向成千上萬的web設計師傳授web易用性方面的只是。是web設計師眼中的頂尖領袖。Jakob Nielsen在1995年發表了“尼爾森十大可用性原則”。
在尼爾森十大原則里有一項是UI一致性原則,我們基于這個梳理出DevCloud的一些細化的點,并給出每個測試因子的權重和分值,計算出各個服務的UI體驗,最后換算成百分值,最后加權計算服務體驗總分。圖4-1就是我們梳理出來的部分規則。
圖4-1 測試分類
2.具體使用puppteer
在上面建立規則之后,我們再針對每個檢測項評估是否可以量化,怎么量化。比如我們想檢測組件的覆蓋度。圖4-2是我們產品所使用的公共組件庫。都是以ave-開頭,checkbox的命名就是ave-button。那普通的checkbox則是以input[type=checkbox]來寫的。我們針對每個服務去掃面線上各個頁面,看使用ave-check和使用原生input checkbox的數量,這樣就能統計出組件庫的覆蓋度。最終驅動各服務去整改。
通過組件的形式使得各個服務體驗基本一致。
圖4-2 DevCloud組件庫
最終通過圖表的形式來進行展示。如圖4-3所示。
圖4-3 ave-checkbox覆蓋度
從圖上我們可以看到ave-checkbox得到整改。
通過以上的方式,我們可以在組件、樣式、以及體驗旅程方面都能很好的把握整個產品設計是否與我們預期是一致的。
我們團隊在自動化方面一直在探索,除了在前端測試、接口測試以及編譯構建方面也一直遵從能夠使用工具提升效率,絕不靠人工來進行檢測的理念,不斷的實踐,極大的減少了人力成本。當然這些能力也一直是對外開放的:華為軟件開發云DevCloud。也歡迎大家來建議和探討。
五、參考資料及擴展閱讀材料
The Front-End Tooling Survey 2018 - Results
尼爾森可用性十大原則
https://www.jianshu.com/p/53daaa5ba794
---------------------------
本文轉自知乎
前端開發
版權聲明:本文內容由網絡用戶投稿,版權歸原作者所有,本站不擁有其著作權,亦不承擔相應法律責任。如果您發現本站中有涉嫌抄襲或描述失實的內容,請聯系我們jiasou666@gmail.com 處理,核實后本網站將在24小時內刪除侵權內容。