2017年12月13日 RN分享

備注

這是很久以前保存的文件败玉,將原始的內(nèi)容放到這里以備不時(shí)之需赶掖。

目錄

1.  為什么要使用RN
    1.  編程人員永遠(yuǎn)的夢(mèng)想
        1.  一次編寫(xiě),到處運(yùn)行之路
            1.  C/Java/Qt
            2.  write once, run everywhere
        2.  learn once, write everywhere
            1.  Chrome撐起的夢(mèng)想
                1.  Electron/Chrome App
            2.  virtual-dom
                1.  虛擬dom
        3. React
            1. Web
            2. Native
    2.  屏蔽了底層代碼, 學(xué)習(xí)成本低
        1.  我的全棧工程師之路 => 21天精通React
    3.  快速發(fā)版
    4.  性能優(yōu)勢(shì)
    5.  為什么不用Weex
        1.  池建強(qiáng)的博客截圖
2.  React Native Init
    1.  初始框架的搭建
        1.  react-native init jumeiReactNative
    2.  多項(xiàng)目的改造
        1.  引入
    3.  React Native 工具包
        1.  Chrome Developer Tools 
        2.  react-devtools
            1.  安裝時(shí)需要在npmrc中指定electron地址: `ELECTRON_MIRROR=http://npm.taobao.org/mirrors/electron/`
3.  React Native工程化
    1.  配置系統(tǒng)(接口開(kāi)關(guān))
        1.  平臺(tái)控制
            1.  項(xiàng)目開(kāi)關(guān)
                1.  總開(kāi)關(guān)
                1.  失敗次數(shù)控制
                1.  系統(tǒng)版本控制(Android/iOS)
                1.  Rom版本控制(安卓定制系統(tǒng), iOS具體版型(iOS6/7/8))
                1.  客戶端版本控制
                1.  CPU版本控制
        當(dāng)檢測(cè)到可以開(kāi)啟RN后, 由客戶端下載bundle包
        2.  Module同步(bundle包下載)
            1.  調(diào)用接口,獲取最新bundle列表
            1. 依次檢測(cè)本地是否已下載過(guò)bundle包
                檢測(cè)標(biāo)準(zhǔn): 
                    1.  文件名相同
                    1.  版本號(hào)相同
                    1.  文件簽名相同 
                未下載 => 啟動(dòng)下載流程
                1.  bundle下載
                    1.  下載失敗
                        1.  網(wǎng)絡(luò)異常
                        1.  存儲(chǔ)空間不足
                        1.  解壓縮失敗
                        1.  校驗(yàn)不通過(guò)(文件hash不對(duì), 文件名不對(duì))
                    1.  下載成功
                        1.  校驗(yàn)并保存文件
                已下載 => 跳過(guò)
        3.  啟動(dòng)RN
            1.  本地是否有對(duì)應(yīng)bundle
                1.  存在 => 載入bundle
                    1.  RN啟動(dòng)
                        1.  活動(dòng)流程是否正常(日常測(cè)試)
                        1.  原生通信是否正常, 是否可以正常調(diào)用原生功能(RN項(xiàng)目測(cè)試)
                            1.  檢查調(diào)用原生功能情況
                                1.  頁(yè)面跳轉(zhuǎn),返回,讀取本地存儲(chǔ),本地通知,Dialog,Toast彈出
                2.  不存在 => 降級(jí)啟動(dòng)H5頁(yè)面                    
    2.  日志記錄與上報(bào)
    3.  測(cè)試過(guò)程中的Tips
4.  爬坑之路
    2.  按路徑引入
    3.  setState
5.  資源推薦
    1. [React Native標(biāo)準(zhǔn)文檔](http://reactnative.cn/docs/0.51/getting-started.html)
    2. [React Native小書(shū)](https://hydrographer-vivian-23728.netlify.com/)
    4. [React 樣式表手冊(cè)](https://shenbao.github.io/ishehui/html/RN%20%E5%9F%BA%E7%A1%80/React%20Native%20%E6%A0%B7%E5%BC%8F%E8%A1%A8%E6%8C%87%E5%8D%97.html#)
    5. [React Native動(dòng)畫(huà)進(jìn)階(中文版)](https://future-challenger.gitbooks.io/react-native-animation/content/)
    3. [構(gòu)建 F8 App / 官方React Native 開(kāi)發(fā)指南](https://f8-app.liaohuqiu.net/tutorials/)
    6. [Redux 中文文檔(勸退指南)](http://cn.redux.js.org/)
6.  劣勢(shì)
    1. 還處于快速發(fā)展期, 頻繁更新
    2. 性能和原生頁(yè)面畢竟還是有差距, 不能繪制過(guò)于復(fù)雜的動(dòng)畫(huà) 

正文

大家好, 今天由我和孫陽(yáng)來(lái)為大家做一下React Native的分享. 在這次的分享里, 我會(huì)先簡(jiǎn)單介紹一下React的相關(guān)知識(shí)和選用React Native的原因, 然后由孫陽(yáng)來(lái)為我們?cè)敿?xì)介紹下React Native具體的工程化過(guò)程, 最后會(huì)介紹一些項(xiàng)目實(shí)施中遇到的坑和相關(guān)的學(xué)習(xí)資源.

讓我們先從React開(kāi)始. React是Facebook編寫(xiě)的一套前端框架. 在React之前, 大家寫(xiě)HTML的思路是按標(biāo)簽去寫(xiě), p標(biāo)簽a標(biāo)簽之類(lèi)的, 然后如果想寫(xiě)一個(gè)復(fù)雜點(diǎn)的功能的話就需要把這些標(biāo)簽全都摞起來(lái), 一個(gè)個(gè)的調(diào)位置. 這種思路在標(biāo)簽量小的情況下還好, 但是標(biāo)簽量一大就會(huì)很難辦, 一大坨標(biāo)簽密密麻麻擠一堆, 誰(shuí)都維護(hù)不了. 當(dāng)然了, 在真實(shí)工作中碰到這種問(wèn)題我們也是有解決辦法的, 就是結(jié)構(gòu)化編程, 把標(biāo)簽按功能拆分開(kāi), 每個(gè)功能區(qū)之間互相獨(dú)立互不影響, 這樣一個(gè)頁(yè)面無(wú)論再怎么復(fù)雜, 都可以通過(guò)拆分的方式把它分成一個(gè)個(gè)的小塊, 我們只要組織好這些小塊就行了. 如果我們?cè)俳o這些小塊起一個(gè)專用的名字, 比如說(shuō)組件 => vue1.0 就誕生了. 但為什么這個(gè)思路只是vue1.0 不是React呢, 因?yàn)樵谖覀儎偛诺臉?gòu)想里, 組件和網(wǎng)頁(yè)元素標(biāo)簽還是一一對(duì)應(yīng)的, React比這更近一步, 他在組件和元素標(biāo)簽之間引入了一層虛擬dom, 組件被映射成虛擬的dom結(jié)構(gòu), 然后再由框架將這些虛擬的dom元素轉(zhuǎn)換成真正的HTML標(biāo)簽列表.

ok, 關(guān)鍵的地方來(lái)了. React的界面是由組件構(gòu)成的, 而我們知道安卓和iOS的界面也都是由和組件類(lèi)似的控件構(gòu)成的, 那么, 有沒(méi)有可能利用虛擬dom這個(gè)中間層, 把React的組件給轉(zhuǎn)換成安卓和iOS的組件呢?如果再加上底層庫(kù)的配合, 讓js可以請(qǐng)求網(wǎng)絡(luò)/存儲(chǔ)數(shù)據(jù)/觸發(fā)彈窗/記錄日志的話, 對(duì)于純數(shù)據(jù)的展示, 是不是就可以直接用React去寫(xiě)了呢? 當(dāng)然, 這些問(wèn)題我們現(xiàn)在都已經(jīng)知道答案了, 2015年4月, React Native第一版上線, React開(kāi)始支持iOS平臺(tái), 2015年9月, React Native正式支持Android的開(kāi)發(fā). 至此, 如果你會(huì)寫(xiě)React的話, 相當(dāng)于你不光能寫(xiě)網(wǎng)頁(yè), 同時(shí)也能寫(xiě)Android和iOS的應(yīng)用.

而且問(wèn)題在于, 跟iOS和Android開(kāi)發(fā)比起來(lái), React確實(shí)要更簡(jiǎn)單. 如果你是一個(gè)原生開(kāi)發(fā)人員, 系統(tǒng)自帶的數(shù)據(jù)庫(kù)存儲(chǔ)要會(huì), 文件系統(tǒng)結(jié)構(gòu)要會(huì), 進(jìn)程線程模型要知道, 事件模型要知道. 但是如果只是為了展示數(shù)據(jù)進(jìn)行交互的話, 根本不需要了解這些系統(tǒng)底層的知識(shí), 只要知道展示文本用Text組件, 展示圖片用Image組件就夠了. 而且, React發(fā)版速度也很快. 因?yàn)镽eact 項(xiàng)目就是一個(gè)js文本文件, 發(fā)版的時(shí)候只要把這個(gè)文本文件傳到網(wǎng)上, 更新下配置就可以.

總結(jié)一下: 對(duì)于展示頁(yè)面來(lái)說(shuō), React 技術(shù)棧 入門(mén)簡(jiǎn)單, 開(kāi)發(fā)效率高(一次編寫(xiě), 三端運(yùn)行), 發(fā)版速度快, 作為技術(shù)人員我們實(shí)際上沒(méi)什么理由不用React. 當(dāng)然, 有同學(xué)可能會(huì)問(wèn), Vue技術(shù)棧下邊也有和React Native相同的Weex, 為什么我們不直接沿用現(xiàn)在前端的技術(shù)棧, 而是要用一個(gè)全新的React技術(shù)棧呢. 這就是React 的另一項(xiàng)優(yōu)點(diǎn)了: 社區(qū)大,坑少.

React 2013年首次對(duì)外發(fā)布, 15年推出Native框架, 現(xiàn)在京東, QQ, 去哪兒都在大量使用React Native相關(guān)的技術(shù)棧, 可以說(shuō)是一套比較成熟的框架了. 但是基于Vue的Weex, 這個(gè), 也不多說(shuō)啥. 前段時(shí)間極客邦基于Weex推出了一款A(yù)pp, 這是他們?cè)诮Y(jié)項(xiàng)后的感謝辭: 感謝Weex團(tuán)隊(duì), 感謝張小龍幫忙協(xié)調(diào)資源, 然后在這么強(qiáng)的支持下, 極客時(shí)間項(xiàng)目整體延期, 10月17號(hào)iOS上線, 12月8號(hào)安卓才發(fā)布上線...然后, 如果我們的人脈沒(méi)有那么強(qiáng), 請(qǐng)不動(dòng)張小龍, 也找不到Weex開(kāi)發(fā)組, 然后這樣的話, 你們都懂.

介紹完React Native, 我們來(lái)講下它的具體使用.

首先當(dāng)然是執(zhí)行react-native init jumeiReactNative初始化項(xiàng)目, 然后npm install安裝依賴, react-native run-android 啟動(dòng)debug模式. 這些官網(wǎng)上都有, 我這兒就不多說(shuō)了.
重點(diǎn)要介紹的是這兩個(gè)地方:

  1. 首先, 我們來(lái)看下RN的代碼, 他這個(gè)就是React的代碼, 沒(méi)有其他多余的東西. 也就是說(shuō), React Native確實(shí)像他描述的一樣, 只要會(huì)寫(xiě)React 就能寫(xiě)React Native. 沒(méi)有其他學(xué)習(xí)成本
  2. 因?yàn)镽eact Native的代碼只是一層皮, 他的本質(zhì)是被編譯好了的, 隨時(shí)可以修改的js, 因此React Native的代碼可以和普通的js代碼一樣調(diào)試, 而且還可以直接在Chrome瀏覽器里打日志, 單步調(diào)試. 就像這樣(開(kāi)啟遠(yuǎn)程調(diào)試功能, 展示Chrome瀏覽器下的日志打印和單步調(diào)試功能)
  3. 除了這些, 我們還可以直接用react-devtools查看組件的效果(展示react-devtools的效果). 不過(guò)這里有個(gè)小坑, 因?yàn)檫@個(gè)工具用到了electron, 而electron的安裝地址又被國(guó)家屏蔽了, 所以安裝工具的時(shí)候經(jīng)常會(huì)因?yàn)榫W(wǎng)絡(luò)異常失敗. 所以我們需要在系統(tǒng)的npmrc配置里指定electron的安裝源才行.
    1. 然后順帶講一下, 他這里的electron實(shí)際上跟我們的RN是一樣的, 也是提供一個(gè)殼, 然后里邊實(shí)際跑的是js代碼. 比如現(xiàn)在前端開(kāi)發(fā)常用的VS Code 編輯器, 實(shí)際上就是用Chrome瀏覽器加上HTML畫(huà)出來(lái)的. 15年之后各種桌面系統(tǒng)的原生開(kāi)發(fā)在事實(shí)上已經(jīng)停滯了, 現(xiàn)在新出的軟件都是用js+chrome瀏覽器外殼去實(shí)現(xiàn). React Native其實(shí)只是這種浪潮下的一個(gè)分支而已.

然后, 關(guān)于RN的基礎(chǔ)知識(shí)已經(jīng)講的差不多了, 下面讓我們請(qǐng)孫陽(yáng)來(lái)為我們介紹下聚美RN的具體實(shí)施過(guò)程.

孫陽(yáng)部分

ok, 孫陽(yáng)分享完了測(cè)試的要點(diǎn), 我來(lái)分享下RN項(xiàng)目在開(kāi)發(fā)時(shí)的一些坑.

先是一個(gè)小坑:

  1. 按路徑引入
    1. react-native里有一個(gè)小問(wèn)題, 就是它默認(rèn)只能用相對(duì)路徑去引入模塊. 這樣就意味著我們?cè)趯?xiě)代碼的時(shí)候要寫(xiě)一大堆的"../.."去回到根目錄, 而且代碼目錄越深".."就用的越多, 寫(xiě)起來(lái)非常惡心.
    2. 不過(guò)RN提供了一個(gè)hack的方式, 就是我們可以通過(guò)在指定目錄下添加一個(gè)package.json的文件來(lái)給一個(gè)目錄指定模塊名, 比如, 我們可以在src目錄下添加一個(gè)package.json, 內(nèi)容是{ "name": "src" }, 這樣src這個(gè)目錄就會(huì)被RN識(shí)別為src模塊, 以后引用的時(shí)候就可以直接引了
    3. 之所以說(shuō)這是一個(gè)坑是因?yàn)檫@個(gè)解決方案在中文網(wǎng)絡(luò)里沒(méi)有, 是在Github的一個(gè)issue里找到的, 所以專門(mén)提一下

然后有一個(gè)狀態(tài)管理的大坑.
RN的樣式展示和邏輯代碼是分屬與兩個(gè)線程的. 當(dāng)邏輯線程更新了組件狀態(tài), 樣式展示代碼就會(huì)根據(jù)新?tīng)顟B(tài)去渲染組件. 這個(gè)看起來(lái)沒(méi)什么問(wèn)題, 但是在實(shí)踐的時(shí)候出現(xiàn)了這種情況, 就是: 邏輯線程在更新完?duì)顟B(tài)之后自動(dòng)退出, 然后RN所在的Activity也跟著被回收了回去, 這里沒(méi)問(wèn)題, 但是因?yàn)榫€程之間的消息不同步, 然后輪到樣式展示線程的時(shí)候展示線程看到狀態(tài)有更新, 就直接去更新組件, 但是組件又不存在, 導(dǎo)致代碼Crash.
這其實(shí)很坑,因?yàn)闄z測(cè)組件存不存在這種事屬于臟活,而且也是基礎(chǔ)功能, 應(yīng)該由框架自己負(fù)責(zé).我當(dāng)時(shí)沒(méi)想到RN發(fā)展了兩年連這個(gè)功能都沒(méi)做,所以也沒(méi)忘這塊考慮, 導(dǎo)致這一個(gè)bug找了半天. 不過(guò)這個(gè)bug最后是這么解決的: 我們加了一個(gè)onMounted信號(hào)量, 組件載入就設(shè)成true, 組件銷(xiāo)毀就改成false, 然后在每次更新?tīng)顟B(tài)和更新組件前都檢測(cè)一下這個(gè)信號(hào)量, 如果為false就直接返回.這樣才算是解決了.

最后一點(diǎn)就是性能問(wèn)題. 前面說(shuō)了, RN雖然最后會(huì)被翻譯成原生代碼進(jìn)行執(zhí)行, 但是畢竟經(jīng)過(guò)了一層虛擬dom中間層, 導(dǎo)致他的性能肯定會(huì)比真正的原生要差一點(diǎn).因此RN不適合展示復(fù)雜的動(dòng)畫(huà), 這點(diǎn)需要注意.

好了, 最后再介紹一下RN的學(xué)習(xí)資源

首先是官方文檔, 這個(gè)不用說(shuō)了, 從搭建環(huán)境到實(shí)際開(kāi)發(fā), 肯定要經(jīng)常翻看的.

然后是React Native小書(shū), 這是一本由中國(guó)開(kāi)發(fā)者寫(xiě)的RN介紹, 建議搭建完環(huán)境后就直接看這本書(shū), 在引領(lǐng)入門(mén)方面寫(xiě)的比文檔要好.

然后是RN支持的全部樣式表和RN的動(dòng)畫(huà)手冊(cè), 這塊前端同學(xué)在開(kāi)發(fā)的時(shí)候肯定要翻的.

最后是一個(gè)Facebook官方的示例代碼, 和Redux使用指南. 官方示例這個(gè)就不說(shuō)了, 直接看就行. Redux這個(gè)要說(shuō)一下. 一般來(lái)說(shuō)大型React系統(tǒng)都需要上Redux去管理組件的各種狀態(tài), 但是如果是小項(xiàng)目的話, 文檔和我的建議都是不要上這個(gè), 對(duì)于我們平常用的小頁(yè)面來(lái)說(shuō), 它帶來(lái)的復(fù)雜度的提升會(huì)遠(yuǎn)遠(yuǎn)大于引入他所能獲得的在開(kāi)發(fā)效率上的收益.

我們的分享講完了, 謝謝大家

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市末秃,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌,老刑警劉巖夸政,帶你破解...
    沈念sama閱讀 216,372評(píng)論 6 498
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場(chǎng)離奇詭異榴徐,居然都是意外死亡守问,警方通過(guò)查閱死者的電腦和手機(jī)匀归,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,368評(píng)論 3 392
  • 文/潘曉璐 我一進(jìn)店門(mén),熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)耗帕,“玉大人朋譬,你說(shuō)我怎么就攤上這事⌒丝眩” “怎么了徙赢?”我有些...
    開(kāi)封第一講書(shū)人閱讀 162,415評(píng)論 0 353
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)探越。 經(jīng)常有香客問(wèn)我狡赐,道長(zhǎng),這世上最難降的妖魔是什么钦幔? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 58,157評(píng)論 1 292
  • 正文 為了忘掉前任枕屉,我火速辦了婚禮,結(jié)果婚禮上鲤氢,老公的妹妹穿的比我還像新娘搀擂。我一直安慰自己,他們只是感情好卷玉,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,171評(píng)論 6 388
  • 文/花漫 我一把揭開(kāi)白布哨颂。 她就那樣靜靜地躺著,像睡著了一般相种。 火紅的嫁衣襯著肌膚如雪威恼。 梳的紋絲不亂的頭發(fā)上,一...
    開(kāi)封第一講書(shū)人閱讀 51,125評(píng)論 1 297
  • 那天寝并,我揣著相機(jī)與錄音箫措,去河邊找鬼。 笑死衬潦,一個(gè)胖子當(dāng)著我的面吹牛斤蔓,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播镀岛,決...
    沈念sama閱讀 40,028評(píng)論 3 417
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼弦牡,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼!你這毒婦竟也來(lái)了哎媚?” 一聲冷哼從身側(cè)響起喇伯,我...
    開(kāi)封第一講書(shū)人閱讀 38,887評(píng)論 0 274
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤,失蹤者是張志新(化名)和其女友劉穎拨与,沒(méi)想到半個(gè)月后稻据,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,310評(píng)論 1 310
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,533評(píng)論 2 332
  • 正文 我和宋清朗相戀三年捻悯,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了匆赃。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 39,690評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡今缚,死狀恐怖算柳,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情姓言,我是刑警寧澤瞬项,帶...
    沈念sama閱讀 35,411評(píng)論 5 343
  • 正文 年R本政府宣布,位于F島的核電站何荚,受9級(jí)特大地震影響囱淋,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜餐塘,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,004評(píng)論 3 325
  • 文/蒙蒙 一妥衣、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧戒傻,春花似錦税手、人聲如沸。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 31,659評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)。三九已至候齿,卻和暖如春熙暴,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背慌盯。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 32,812評(píng)論 1 268
  • 我被黑心中介騙來(lái)泰國(guó)打工, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留掂器,地道東北人亚皂。 一個(gè)月前我還...
    沈念sama閱讀 47,693評(píng)論 2 368
  • 正文 我出身青樓,卻偏偏與公主長(zhǎng)得像国瓮,于是被迫代替她去往敵國(guó)和親灭必。 傳聞我的和親對(duì)象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,577評(píng)論 2 353