????????最近隨著使用ReactNative仪际、公眾號(hào)以及H5項(xiàng)目越來越多,為了統(tǒng)一開發(fā)技術(shù)及標(biāo)準(zhǔn)锨阿、提升邏輯模塊的復(fù)用性、提升開發(fā)效率性宏,于是開始設(shè)計(jì)一套解決上述問題的開發(fā)框架群井,目標(biāo)就是一次開發(fā)毫胜,可以在ReactNative及WebBrowser中運(yùn)行(未來的目標(biāo)會(huì)支持在更多的容器上運(yùn)行)酵使。
一、找輪子
????????大家看到這里可能會(huì)有個(gè)疑問焙糟,這種框架在世界上最大的男性交友網(wǎng)站上應(yīng)該有一大堆穿撮,為什么還要造輪子缺脉?個(gè)人覺得技術(shù)框架攻礼,有能力自己打造還是要自己打造,我們可以去學(xué)習(xí)別人的思路栗柒,最好不要直接使用,即使做出來的輪子可能會(huì)有性能不好或者不好用等問題,但是自己打造的輪子是最可控的太伊,正所謂知己知彼、可進(jìn)可退僚焦。在經(jīng)過一段時(shí)間的摸索了解锰提,目前業(yè)界主流四種解決方案大致如下欲账。
1. 由React.js轉(zhuǎn)換到ReactNative。
????????這個(gè)方案比較適合優(yōu)先考慮H5的開發(fā)團(tuán)隊(duì),由于ReactNative的樣式是CSS3中的子集罢洲,這樣子的轉(zhuǎn)換是有損轉(zhuǎn)換踢故,可能會(huì)影響布局和功能惹苗。目前業(yè)界比較少使用這種方案殿较,沒找到有相關(guān)的資料桩蓉,但是理論上應(yīng)該是可以的淋纲。
2.封裝一套抽象框架院究。
????????這個(gè)方案就是在ReactNative及React.js的上層再抽象出一套開發(fā)框架洽瞬,用于抹平兩者之間的差異伙窃。類似于微軟發(fā)布的ReactXP。這種方案適合于想要追求三端有較高的用戶體驗(yàn)为障,但相關(guān)開發(fā)人員較少的團(tuán)隊(duì)放祟。但是這個(gè)方案有不好的地方,就是增加了開發(fā)人員的學(xué)習(xí)成本鞋喇,同時(shí)很多功能的實(shí)現(xiàn)也受限于抽象框架的完善程度骗奖,目前ReactXP對ReactNative組件的支持還是比較有限醒串。
3.由ReactNative轉(zhuǎn)換到React.js
????????這種方案與第一種相反,它是優(yōu)先在ReactNative中進(jìn)行界面開發(fā)鄙皇,優(yōu)先保證App端的體驗(yàn)及完整性,然后再考慮Web端的可用性缠沈。正如上面所說的,由于ReactNative樣式是CSS3中的子集洲愤,至少在轉(zhuǎn)成H5的時(shí)候顷锰,不會(huì)丟失功能及屬性,在可行性及可用性方案都會(huì)比較有保障肛宋,目前業(yè)界較多使用這個(gè)解決方案,GitHub上面也有很多開源的框架酝陈,例如淘寶的react-web毁涉,國外的react-native-web等,特別是react-native-web使用的用戶也很多穆壕。但是這個(gè)方案也有缺點(diǎn),就是依賴開源框架目前支持轉(zhuǎn)換的組件粱檀,有些基礎(chǔ)組件或者第三方轉(zhuǎn)換的組件未必能及時(shí)跟進(jìn)漫玄。再者压彭,生成的Web頁面的樣式類名及樣式可維護(hù)性較差。
4.用JSX語法(VUE也有)壮不,通過編譯器編譯對應(yīng)的多平臺(tái)
????????這種方案就是利用JSX語法或者VUE的語法询一,這樣子減少開發(fā)人員的學(xué)習(xí)成本隐孽,平臺(tái)間的差異由編譯器抹平解決菱阵,這個(gè)方案從兼容性、體驗(yàn)性來講都會(huì)比較均衡晴及,類似的框架有阿里的Weex和近期京東開源的Taro,這兩個(gè)框架還沒試用過暫時(shí)無法評論琳钉,但是從網(wǎng)友的一些反饋來講蛛倦,Weex坑多,且得靠自己消化溯壶,從Taro的宣傳資料來看,Taro是基于京東的Nerv框架(類React.js躲庄,據(jù)說近期在申請專利钾虐,我有一個(gè)差不多的框架也在申請專利),對于掌握了React.js的開發(fā)技術(shù)的人員來講基本可以無縫對接倔监,但是與第三方組件對接上還未實(shí)現(xiàn)支持。
二浩习、造輪子
????????通過上面4種輪子的比對分析济丘,結(jié)合目前團(tuán)隊(duì)需要業(yè)務(wù)組件及團(tuán)隊(duì)的技術(shù)結(jié)構(gòu) ,我想到了另外一種思路疟赊,就是接受移動(dòng)端及Web端的平臺(tái)間的差異,基于JSX語法(降低學(xué)習(xí)成本)近哟,重點(diǎn)關(guān)注復(fù)用業(yè)務(wù)組件層(代碼多端復(fù)用)鲫寄,按照ReactNative目前已支持的組件及API進(jìn)行抽象疯淫,封裝成對應(yīng)的Web組件戳玫、RN組件及API量九。同時(shí)為了保證Web端的體驗(yàn)适掰,Web的樣式與RN的樣式分離类浪,實(shí)現(xiàn)同一源碼的頁面可以在ReactNative上運(yùn)行,也可以在WebBrowser上運(yùn)行肌似,以后如果業(yè)務(wù)需求需要引入小程序川队,那么可以通過基礎(chǔ)組件庫增加小程序組件進(jìn)行兼容即可力细。此方案的難點(diǎn)在于如何解決樣式問題眠蚂,這個(gè)我將在后面單獨(dú)寫一篇我的踩坑心得來分享∈呕郏基礎(chǔ)架構(gòu)圖如下啄糙。
1.基礎(chǔ)組件庫封裝
????????通過抽象組件隧饼,以ReactNative組件為主沈堡,統(tǒng)一接口及屬性诞丽。第三方組件也需要包裝成為抽象組件,所有的業(yè)務(wù)組件都使用基礎(chǔ)組件庫率拒,保證業(yè)務(wù)組件層可復(fù)用及可跨端禁荒。
2.封裝基礎(chǔ)組件樣式
????????Web端的樣式與ReactNative端的樣式是獨(dú)立兩套樣式角撞,主要是考慮到Web端的兼容性勃痴,RN的樣式雖然是CSS3的子集热康,但是在Web端去應(yīng)用的話就會(huì)有較多的兼容性問題,所以才考慮設(shè)計(jì)為獨(dú)立的兩套樣式姐军,在保證各端的體驗(yàn)性奕锌,又不增加過多的工作量著觉。
3.封裝API
????????為了業(yè)務(wù)組件層的實(shí)現(xiàn)復(fù)用饼丘,還有一層API層需要處理,主要是像ReactNative中提供了很多Web端沒有的API肄鸽,例如導(dǎo)航油啤、設(shè)備調(diào)用等,同樣的H5中也有一些API是ReactNative中沒有的烂斋,例如localStorage、sessionStorage等汛骂。這里采取與組件類似的處理方式即可评腺,封裝一層API抽象層,用于統(tǒng)一API接口調(diào)用蝶念。
4.封裝路由及其他基礎(chǔ)插件
????????由于路由組件Web及ReactNative的版本的導(dǎo)出對象都不一樣媒殉,所以也需要通過抽象接口實(shí)現(xiàn)統(tǒng)一摔敛。Ajax庫直接復(fù)用我自己寫的庫,也可以使用第三方的庫(ReactNative對這一塊的設(shè)計(jì)比較周全马昙,web的http請求可以平移,所以才可以復(fù)用Web上的Ajax庫)攒暇。
三、結(jié)語
????????目前這個(gè)方案已開始在項(xiàng)目中實(shí)施就轧,在造輪子的過程中也總結(jié)到了很多有趣的東西,后續(xù)將陸續(xù)分享出來钓丰。