2017年我們團隊就開始使用ReactNative開發了一些內部管理工具,由於各種問題,我們幾乎都快放棄使用了。但后來因為原生端人手不夠(哭),又重拾使用React-Native開發了一些頁面,發現在和原生的混合開發模式(原生導航、RN純單頁)下,ReactNative頁面作為詳情頁展示非常合適:比H5渲染更快、配合CodePush比Flutter更動態、比原生開發成本更低。但是...ReactNative它看起來這么香,為啥大家都吐槽天天說要棄坑呢。真香是真的,問題多也是真的,我們遇到了一個又一個問題,在這里記錄一下,希望能幫到一些同學。
iOS工程依賴的問題
iOS使用CocoaPods做為依賴工具,我們希望把ReactNative工程作為一個單獨的pod組件依賴進主工程,主工程就不需要依賴ReactNative開發環境了,好在ReactNative各個組件和模塊都提供了podspec文件,使用的時候只需要將podspec轉為json格式,然后上傳至私有pod倉庫即可,注意,這里podspec為私有的,但實際的依賴文件還是會從GitHub下載。下面是我們的RN工程的podspec:
package = JSON.parse(File.read(File.expand_path('../package.json', __dir__))) dependencies = package['dependencies'] react_native_version = dependencies['react-native'] react_native_svg_version = dependencies['react-native-svg'] react_native_code_push = dependencies['react-native-code-push'] Pod::Spec.new do |spec| spec.name = "YOU PROJECT NAME" spec.version = "0.0.1" spec.summary = "XXXX for ReactNative" spec.description = "XXXX for ReactNative" spec.homepage = "https://gitlab.xxxx.com/app-rn/XXXX" spec.license = { :type => 'MIT', :file => 'LICENSE' } spec.author = { "liujixin" => "XXXX@email.com" } spec.source = { :git => "https://gitlab.xxxx.com/app-rn/xxxx.git", :tag => "#{spec.version}" } spec.ios.deployment_target = '9.0' # 業務原生代碼 spec.source_files = "ios/XXXX/Classes/**/*" spec.resources = "ios/XXXX/Assets/*" # React spec.dependency 'React/Core', react_native_version spec.dependency 'React/CxxBridge', react_native_version spec.dependency 'React/DevSupport', react_native_version spec.dependency 'React/RCTText', react_native_version spec.dependency 'React/RCTNetwork', react_native_version spec.dependency 'React/RCTWebSocket', react_native_version spec.dependency 'React/RCTAnimation', react_native_version spec.dependency 'React/RCTImage', react_native_version spec.dependency 'React/RCTPushNotification', react_native_version spec.dependency 'React/RCTLinkingIOS', react_native_version spec.dependency 'React/RCTActionSheet', react_native_version # 第三方依賴,如果官方specs沒有對應版本,需要將對應版本podspec文件上傳至您的私有repo spec.dependency 'glog', '0.3.5' spec.dependency 'DoubleConversion', '1.1.6' spec.dependency 'Folly', '2018.10.22.00' spec.dependency 'yoga', '0.59.5' spec.dependency 'RNSVG', react_native_svg_version spec.dependency 'CodePush', react_native_code_push spec.dependency 'BVLinearGradient', dependencies['react-native-linear-gradient'] spec.dependency 'RNViewShot', dependencies['react-native-view-shot'] end
無法解析本地模塊的問題:
在使用ReactNative幾個月后,陸續開發了很多頁面,也積累了一些組件,在組件開發過程中,發現一個非常蛋疼的問題。就是ReactNative的打包器不支持本地包,如果你使用 "package": "./file/src" 這種方式引入包,會直接報:
Unable to resolve module `XXXX` from `XXX.js`: XXXX could not be found within the project.
查了一下,symlinks在ReactNative中就是不起作用啊我暈 (issues),這還怎么玩,總不至於寫完再手動拷貝到node_modules吧。
手動不可靠也不現實,但是有人就想到了自動拷貝,也算是一種曲線救國的臨時方案吧。
wml是一個幫你自動同步文件的工具,基於fb的watchman,使用簡單,大家可以試一下,在開發組件時,把開發目錄的包自動同步到example工程的node_modules下,這樣就可以愉快的調試了。
推薦直接安裝在本地,然后配置一下啟動wml監聽腳本方便使用:
{ "name": "examples", "version": "0.0.1", "private": true, "scripts": { "android": "react-native run-android", "ios": "react-native run-ios", "start": "react-native start", "wml-start": "node ./node_modules/wml/src/cli/index.js add ../src ./node_modules/react-native-module/src && node ./node_modules/wml/src/cli/index.js start", "wml-stop": "node ./node_modules/wml/src/cli/index.js stop", "test": "jest", "lint": "eslint ." }, }
另外需要注意的是wml依賴watchman,所以必須先安裝watchman,Mac用戶直接用Homebrew安裝即可。
brew install watchman
Windows稍微麻煩點,除了手動安裝配置環境變量之外,還需注意是否缺少dll,另外在啟動wml之前,Windows用戶需要手動把wml安裝目錄加入watchman的監聽:
watchman watch /Users/youname/.nvm/versions/node/v8.9.0/lib/node_modules/wml/src