React Native-应用程序和批评

通常,选择这种语言时,期望为两个平台开发一个应用程序比开发两个应用程序花费一半的时间。 但是最后,事实证明,由于外在的光彩和市场营销所隐藏的困难,发展需要付出的甚至更多。 我们将讨论在使用React Native的最近几个月中遇到的一些类似的困难。


React Native将Javascript用于移动开发。 这是由于他使用多个收集器来构建项目这一事实而实现的-Metro Bundler,它解释JS代码并代表目标系统的资源和收集器。 就我们而言,这是Android的摇篮。 从理论上讲,React Native应用程序应该非常简单地启动。 react-native run-android命令启用Metro Bundler并为所有连接的Android设备和模拟器构建应用程序。


实际上,事实证明,即使在这个阶段也存在困难。 错误“无法下载JS捆绑软件”不断出现在我们的项目中,这意味着捆绑软件无法将代码转换为本地代码。 后来发现,由于它没有启动。 StackOverflow确认了猜测,并建议您应使用react-native start命令在单独的线程中运行捆绑程序。 这使您仅在package.json更改后才重新启动捆绑程序,因为该过程不会减慢开发速度。


Package.json是一个文件,其中包含应用程序的一组外部模块。 在npmjs.com上,存在大量用于React Native的不同库,从而扩展了功能并简化了开发。 许多库(例如Firebase)使用本机函数,因此必须直接与本机代码关联。 为此,请使用react-native link <library-name>命令,该命令应使用本机代码配置这些关系。


由于所有库都是在不同的时间编写的,因此它们使用不同版本的SDK,并且需要使用不同的方法。 有时,可能会发生库之间的不兼容,或者库的最新版本处于试验阶段,开发人员自己建议降级为倒数第二个库。 通常,链接不会配置所有必需的依赖项。 因此,对于上述firebase,您需要在本机代码中添加许多其他库,连接各种外部存储库,修改mainApplication.java(这仅适​​用于android!)。 对于Firebase,有执行这些操作的相当容易理解的说明,但是对于其他库,它并不总是存在。


配置与本机代码的连接后,您可以构建项目,以希望所连接的库能够正常工作。 组装时,值得记住的是,如果遇到错误,则应确保它的出现完全是由于您的操作引起的,而不是由于收集器错误引起的。 为了完全放心,您应该执行以下操作序列:


rmdir node_modules /s /q && npm cache clean - force && npm i 

此命令将删除node_modules文件夹,然后重新加载它。 这是最长的任务之一,因此极少值得使用。 在某些项目中,node_modules最多可以在硬盘驱动器上占用数GB的空间,因此重新安装将花费一些时间。


 rmdir android/app/build /s /q 

在开发过程中,注意到通常无法成功进行构建是由于收集器无法从调试目录创建(或删除)文件夹这一事实造成的。 此操作解决了react无法自行删除文件夹的问题。 但是与此同时,再次从头开始为该文件夹生成文件将花费额外的时间。


 react-native start-reset-cache 

启动Metro Bundler。 在整个调试过程中,此选项卡应保持打开状态。 如果发生错误,则错误日志可能会显示在此处。 最有可能的是,如果发生错误,则此过程将结束,并且需要再次重新启动。


 react-native run-android 

在连接的设备或仿真器上安装应用程序。 大多数构建错误都在这里发生,其中一些是可以理解的,但是有些非常不合理,可以通过重新启动整个过程来“治愈”。


想象一下在连接Firebase之后,针对一个项目的一系列命令(已经具有领域,redux,react-navigation,以及大约十个以上的库)的构建过程。


 react-native start react-native run-android >>    debug react-native run-android >> , metro bundler  react-native start react-native run-android >>    debug react-native run-android >>  !  metro bundler ,   JS-   react-native start >>   restart         -  

不用说,这需要很长时间吗? 这不是一个一次性的过程:到目前为止,程序代码几乎每次更改后,都需要执行此过程。 随着每个新库的出现,项目变得越来越不稳定,而且此过程可能会更改,通常情况更糟。 调试应用程序是开发人员最重要的功能之一,在这种情况下,其速度会大大降低。


说到调试。 React Native调试器不仅存在启动方面的问题。 纠正由于测试而发现的错误也是一个相当痛苦的过程。 在react-native中,JS代码被翻译成本机代码,但是在翻译过程中被混淆了。 因此,如果您不想看到“ zzz.yyy()中的空指针异常”之类的错误,那么您需要使用内置的调试器,您不仅可以读取logcat中的异常。 发生错误时,调试器将显示带有描述的红色“死亡屏幕”,或多或少地将其推向纠正路径。 但是这部分存在问题。


好吧,当错误看起来像这样:



很清楚,这里发生了什么-变量中未定义this.state.noteArray.map而不是预期的数组对象,这导致了臭名昭著的TypeError。 您可以通过以下步骤来修复它:app.js:14并在使用前检查此变量中的值。


当错误看起来像这样时更糟:



因此:



大概:



图片是从互联网上拍摄的,但我们看到了它们的实时图像。 尽管它们在运行时中显示,但该错误并不是由于您的代码中的某些操作不正确所致。 这可能是由于您错误地安装了库,或者您的导入具有不兼容的依赖项,或者本机代码出了点问题,而React试图捕获该错误。 每个错误都是个体的,解决的方式也非常不同。 最好有StackOverflow和至少某种调试模式。


更糟的是,在调试中未重现错误时。 在尝试使用支持Android x64架构的新版React构建应用程序时,我们遇到了这种情况。 使用调试器安装应用程序时,一切正常。 但是,一旦我们在电话上构建了测试仪,与数据库进行交互时,一切都会停止工作并中断。 要快速调试非调试,我们使用控制台消息,在这种情况下,这是react toastAndroid组件。 该组件在到达特定代码行时显示简短文本。 有条不紊地,最好将代码分成两半,我们将发生错误的函数本地化,并发现Object.assign({},item)方法在新版本的React中不起作用。 幸运的是,您可以在保持应用程序功能的同时用较短的{... item}替换此功能,但是搜索该错误大约需要花费十几个小时的时间。


经过小型研究以寻找原因。 事实证明,React Native使用不同的Javascript引擎在调试和生产版本中解释JS代码:用于调试Chrome JS引擎和JavaScriptCore。 是的,React Native不会将JavaScript转换为本地代码,而是在运行时进行解释。 同时,调试引擎的工作更加稳定,因此错误越来越多地潜入生产环境。 例如,本文介绍了日期格式在不同条件下如何工作。 返回错误:事实证明,在更新React Native版本之后,生产生产Web引擎失去了对Object.assign()的支持。 但是调试引擎保持不变。


也许最糟糕的选择是当应用程序随机中断,仅在生产版本中中断,而没有来自React Native的任何日志时。 示例:在手机上安装该应用程序的发行版后,它会“运行一段时间”,然后“随机关闭,而不会出现错误或警告”。 此外,该错误不会在所有设备上重现。 最后,通过反复试验(并检测到上述Firebase Crashlytics没有发送相应的错误),我们设法捕获了如下所示的下降日志:



该文本甚至不适用于我们的应用程序,甚至没有用红色标记。 但是,在获得并进入论坛后,我们发现新版本的React Native已被破坏。 而上一个被打破了。 在官方的Issue Tracker上,错误“ Android崩溃:信号11(SIGSEGV)”存在了两个月,并且幸运的是,在我们去那里的前两天(!),提出了一个解决该错误的实验性解决方案。


具有讽刺意味的是,某些不得不处理Android Studio的开发人员对IDE具有诸如build / cleanproject或file / invalidate caches之类的选项感到困惑。 为了摆脱错误消息和警告以及同步错误带来的gradle异常行为,这是必需的。 开发人员问:“为什么要为IDE做这些工作,在这种情况下,这些命令应该自动执行。” 它们是可以理解的,但是与此同时,现代的IDE在后台完成了所有困难的工作。 这些开发人员根本不使用React Native。


以上所有都是过去几周发生的孤立案例。 在这里我们没有描述使用Expo运行应用程序的复杂性,而是在babel / eslint中设置了代码样式,我们没有因为过多的灵活性而责骂Javascript,也没有透露由于redux / realm链接导致的调试几乎完全丢失了其中一个项目。 考虑到所描述的支持和开发困难以及两个系统都乘以2的事实,是否值得考虑React Native是否真正盈利? 用这种语言完成我们的第三个项目后,我们决定不这样做。 你觉得呢

Source: https://habr.com/ru/post/zh-CN468901/


All Articles