2018 年 10 月13 日,由又拍雲和知曉雲聯合主辦的 Open Talk 丨2018 小程序開發者沙龍系列活動廣州站拉開帷幕,糗事百科前端負責人宋航在沙龍上作了《更App化的小程序開發》的分享。html
「2018 小程序開發者沙龍」是又拍雲 Open Talk 繼「2018 音視頻技術沙龍」後推出的重磅系列活動,與大部分偏重營銷、流量的小程序活動不一樣,本系列活動更熱衷於分享小程序開發過程的種種有趣經歷和有益的經驗。前端
宋航目前負責糗事百科的前端、小程序、小遊戲相關的開發工做,對遊戲開發、App 開發、Web 前端開發都有深刻研究,追求開發好玩的產品。糗事百科在小程序上除了延伸自家產品製做了「糗事百科+ 」小程序外,還在以好玩、有趣爲目標的道路上製做更多優質的小程序,好比在塗鴉方面的「填色心語」等。小程序
宋航認爲,小程序肩負着強化 Web 能力、簡化 App 開發的重大責任,一樣是使用 Javascript 開發,不少人把 「Web 頁面開發「的一套東西搬到小程序開發上,所以不得其法。在分享中,宋航介紹了借鑑 App 開發來作小程序的思路和方法,內容主要包括:瀏覽器
如下是分享整理:緩存
你們下午好,很是開心能在 Open Talk 的活動上給你們分享糗事百科團隊一年多以來的小程序開發經驗。我是來自糗事百科的前端開發負責人宋航,今天分享的主題是「更 App 化的小程序開發」。安全
在小程序發佈的一年多以來,糗事百科把自家的 App 產品落地到小程序,並且開發了不少比較好玩的小程序。這些小程序不必定是用戶量很高的產品,可是對於你們在小程序開發探索路上會有很大的幫助。微信
2016 年末微信發佈小程序,那個時候功能相對較少。簡單的說就是 H5 的「微信化」,在微信裏畫了一個 H5 框架。可是今天小程序有更多的硬件能力,因此我今天才會分享《更 App 化的小程序開發》的主題。個人見解是無論是目前仍是將來,小程序能夠替代不少 App。網絡
你們認爲小程序的出現意味着什麼呢?對於開發者來講,我以爲小程序的出現其實「增強了 Web 的能力,簡化了 App 的開發」。併發
小程序在 Android、iOS 均可以運行,可是它相比於 App 有什麼不一樣?在開發方面,可能早上有一個想法,晚上就能夠開發出一個小程序而且實現上線;而開發 App,不可能早上有一個想法,晚上就完成開發併發布到各類各樣的應用商店。框架
第一,小程序與 H5 有什麼不同?
小程序比 H5 有更多的能力,兼容性更好。前端開發者都知道各類瀏覽器的兼容是一個痛點,小程序的出現首先解決了兼容問題,一樣的運行環境能夠屏蔽掉不兼容的一些錯誤,讓咱們更專心於開發業務邏輯。
第二,小程序有更強的硬件能力。
例如把頁面上的圖片保存到手機相冊,普通 H5 很難作到。在小程序裏面,微信爲了防止小程序濫用硬件能力,引入了一個概念——受權,這個概念在 App 裏面已經有了。爲何小程序要有受權呢?由於「能力越大,責任越大」,微信能夠賦予小程序更強的硬件能力,可是爲了不這種能力被亂用,必須加入受權這一律念。若是 H5 可以隨便修改相冊、修改聯繫人,那是一種很恐怖的事情。經過微信和受權機制,小程序能夠調用到手機的各類硬件能力,相比 H5 有更大的想象空間。好比說咱們如今作的直播、錄像、拍照的功能均可以用到手機攝像頭、麥克風、相冊等,甚至能夠把文件傳到小程序,這個時候,咱們產品能夠擁有很大的想象空間。
第三,小程序背靠「微信」的用戶系統、推送、支付,有利於商業運營,讓開發者節省了不少開發工做。H5 沒有推送功能,要從新喚回用戶須要費不少工夫,好比搞活動等。簡單說一下 H5 的主要邏輯,如這張圖:
△ H5 的數據邏輯
H5 的主要邏輯均可以劃分爲這個流程,經過請求網絡數據、處理數據展現到用戶面前,用戶作出的任何操做,好比點贊、發評論返回到網絡,請求回網絡以後送回內容。
對比 H5,小程序上有更多的硬件能力,小程序不只能從網絡上獲取數據,還能夠從硬件設備獲取數據。
△ 小程序的數據邏輯
糗事百科團隊早期作小程序開發時,因爲產品比較普遍,迭代比較快,因此沒有采用第三方框架,而是採用了官方的開發文檔來工做。
△ 糗事百科早期開發小程序的邏輯
官方的小程序開發文檔其實很簡單,咱們控制對應的 page.js,經過設置 data,渲染到頁面即 wxml,讓它展現 UI 顯示、動畫效果和操做反饋。隨着開發的深刻,咱們漸漸發現整個程序變得很是臃腫,由於小程序的邏輯代碼都放在了 page.js 裏面。一些資料裏面提到小程序跟 H5 有一個很大的區別就是在跳轉頁面的時候咱們不知道怎麼傳遞數據,由於每個 page.js 都是孤立的。資料裏面也會教你如何去傳遞數據,可是作起來會很是麻煩,每當你建立一個 page.js,你就須要思考這個數據在下一個頁面會不會用到,這個數據改了之後上一個頁面應該怎麼去從新渲染,當頁面不少的時候就回變得很是複雜,這樣會影響到咱們每一次作新頁面的開發。
糗事百科團隊在重構代碼的時候,沒有采起第三方框架,在原來基礎上把整個 MVC 框架套進去。小程序官方提供的 page.js 能夠想象成 MVC 框架下的 Controller ,咱們把須要用到的數據抽象成模型,每一個模型能夠在不一樣的 page.js 上,經過 page.js 修改 data,最後改到 UI 上。
△ 糗事百科應用 MVC 後開發小程序的邏輯
咱們看下每一個步驟負責的內容。原來負責全部邏輯的 page.js 如今只須要負責從 Model 接收數據、響應及管理 View 的生命週期。數據模型作的事情比較簡單,處理業務邏輯、提供數據給 page.js、數據持久化。
△ Model 和 Controller 的數據傳輸
數據模型和 Controller 是經過怎麼樣的邏輯進行數據傳輸的呢?這裏運用的是「觀察者模型」和「發佈/訂閱模型」,這兩個模型均可以很好地在 Controller 和 Model 之間傳遞數據。這兩者有什麼區別呢?
「觀察者模型」能夠把 model 的屬性,好比文章的點贊功能,是否已經點讚的屬性,與 Controller 中的 data 相互綁定,在修改 model 的時候,直接修改 Controller 裏面的 data,而後執行 setData 方法,讓 UI 上的點贊按鈕被點亮。
△ 「點贊」動做的數據傳遞
在 UI 上咱們經過綁定事件,讓點贊按鈕與 page.js 的邏輯綁定,當點贊事件發生,文章的實例會改變點讚的屬性,由於雙方是互相綁定的,因此 page.js 裏面的 data 也會改變,從而執行 setData 方法。
「觀察者模型」比較偏向於單個的屬性變化,好比用戶登錄,登錄以後有不少屬性好比名字、頭像、性別都發生改變,若是每個都用「觀察者模型」,每一個屬性變化都要執行 setData,setData 會用得很是頻繁,官方文檔是不建議這麼頻繁去調 setData 方法。因此「觀察者模型」比較適用於當數據變化時不會影響到其餘改變 UI 數據變化,好比點贊按鈕只會影響點讚的 UI 有沒有被點亮,不會影響其餘數據改變,因此沒改變一次,只調用一次 setData 方法,不影響整個程序的性能。要注意的一個地方是「觀察者模型」須要綁定,在 Controller 的生命週期裏要注意它的解綁和綁定。
「發佈/訂閱模型」在跨頁面傳遞數據的時候用得比較多,好比前面說的用戶登陸的例子,用戶登陸以後可能涉及到幾個頁面的更新, 若是上個頁面也有用戶信息的展現也須要更新,若是是大型的軟件可能涉及的更新數據會更多。若是按照官方的說法把整個數據 setData 一遍會顯得太過繁瑣,
「發佈/訂閱模型」適用於跨越多個頁面同時操做 UI 更新,讓互相關聯的 data,在某個時間點下一塊兒更新,不用頻繁的去 setData。好比登錄以後用戶頭像、性別等進行改變,咱們只須要一次setDada 就能夠。一樣「發佈/訂閱模型」也要須要綁定,綁定的時候也要注意一下解綁,重複綁定。
△ 登錄模型示意圖
上圖是登錄模式示意圖,經過綁定事件,在 Login Event 發生以後,Pub-Sub 推送到每一個 page.js ,多個頁面同時更新。
△ model 管理數據
經過抽象的一個 model,整個程序變得很簡單,小程序不只僅能從網絡獲取數據,還能夠從硬件設備好比說存儲空間裏面獲取數據。前面咱們說過把 page.js 裏面的 data 抽象成一個 model,每次拿數據會通過上圖的三個步驟:首先查內存是否有這個數據,若是沒有能夠從本地緩存查找,最後咱們再從網絡/ 硬件設備去查詢,這些操做均可以封裝會 model 裏面,這樣調 model 的時候很簡單地調一個屬性,它底層就已經通過三層查詢,這樣不只基於咱們的網絡請求,還能夠很很簡單利用小程序提供的緩存空間和文件系統空間
MVC 框架在開發上對咱們有很大的幫助,讓數據流脫離出 page.js,不用再去考慮各類數據的傳遞,微信在跳轉頁面的時候只容許在 URL 上攜帶必定的字符串,經過這樣的方式傳遞到下一個頁面,致使對象類型很難去傳遞了。
如何讓小程序更快地展現出內容給用戶?這個是在作網頁的時候常常遇到的問題,網頁加載慢1秒就可能損失大量的用戶,作小程序也是如此。
第一步把小程序代碼量儘量壓縮資源。不少人剛作小程序的時候,認爲能夠讀本地資源的圖片,不用從網絡加載,把本地資源的圖片塞在小程序裏,其實這並非一個很明智的方法,不少圖片能夠放到網絡上,不必定塞到小程序包裏面。
第二步是分包。這有點像作 H5 的時候,把 JS 包劃分出來,咱們能夠把訪問頻率比較低的頁面分到分包裏。如今小程序是 4M 的主包加 2M 的分包,咱們能夠把訪問頻率很低的頁面好比設置頁面、用戶須知頁面,塞到分包,這樣整個小程序包變得比較小,主包變小下載速度比較快。
這個時候咱們能夠很快進入第二階段,就執行咱們的業務邏輯。
△ 小程序的首屏優化
小程序一打開執行的業務邏輯是訪問網絡,並不必定要等到進到相應的 page.js 才把數據請求出來。每次訪問小程序頁面的時候,都在讀取 model 裏面的數據,model 裏面數分紅 3 層。咱們能夠把用戶上一次退出小程序的狀態保存到緩存,等咱們再進去的時候就能夠看到數據了,並非每次進去都是一個白屏 loading。
渲染內容要注意的一點是「首次渲染」能夠渲染出比較簡單的東西,隨着頁面寫得愈來愈深刻,wxml 內的邏輯層級會比較複雜,這時候能夠用小程序提供的組件或者模版,把每一個部分封裝成組件,每一個組件渲染的時候內部會進行數據的優化,不會影響整個頁面的複雜度,渲染起來比較簡單快捷。
對於小程序,「能力越大,責任越大」。一個小程序擁有硬件能力時須要注意的是什麼呢?微信給與了小程序調用硬件能力的受權,可是我看到不少小程序在受權上都作得不好,好比一進去點了拒絕,找不到從新受權,點了拒毫不會再出現受權了。
小程序在獲取一些隱私的東西的時候,好比手機號碼、用戶信息等,之前作 Web 端可能沒有注意到這方面的安全性。微信提供的手機號碼是加密的數據,不少人拿到數據後臺解密,而後明文傳輸給前臺,這種作法是不理智的,咱們在數據傳輸上要注意加密的信息。
在受權上,使用小程序給咱們提供的 Api 接口來受權,一旦拒絕就不會出現提示,如今廣泛的作法是使用按鈕,按鈕來喚醒受權,即便點拒絕了,從新用按鈕點擊受權仍是會彈窗,因此最理想的狀況是有一個頁面讓用戶清楚知道本身在哪一方面授了權,這就是咱們在擁有了這些能力以後要給用戶一個明確的反饋。
善用微信提供的能力,微信提供給咱們有不少東西。好比咱們以前作一個電商平臺,寫了半天用戶填寫信息的框架,後來發現微信已經給咱們提供了一個地址選擇的功能,包括卡包功能,微信都已經內置在裏面。固然微信的 Api 上內容比較多,你們每次開發的時候都須要看一下,我每次看它的開發文檔,它擁有的新功能是不少的。
咱們在小程序上還能獲取到各類各樣的網絡狀態,好比在作一些視頻播放類小程序,或者大流量的應用,能夠利用這些網絡狀態來提示用戶是否選擇打開一些功能。這些都是小程序賦予咱們硬件能力以後,咱們可以改善小程序用戶體驗的地方。
推薦閱讀(演講視頻及ppt):更 App 化的小程序開發 - 又拍雲