当前位置: 首页 > news >正文

React Native架构革命:从Bridge到JSI性能飞跃

React Native 的架构经历了从旧架构(基于 Bridge)到新架构(基于 JSI、Fabric、TurboModules)的重大变革。下面通过一张 Mermaid 流程图来直观对比其核心变化,并为您解析其演进原因。

深度解析React Native底层核心架构

flowchart TDsubgraph OldArch [旧架构 (Bridge模式)]direction TBA[JS线程<br>业务逻辑与UI布局] -->|1. 序列化为JSON| B(Bridge<br>异步消息队列)B -->|2. 传递| C[Native/UI线程<br>渲染原生视图]B -->|2. 传递| D[Shadow线程<br>Yoga计算布局]D -->|3. 布局信息| CC -->|4. 反序列化执行| E[原生模块<br>启动时全量初始化]endsubgraph NewArch [新架构 (JSI + Fabric + TurboModules)]direction TBF[JS线程<br>通过JSI直接持有Native引用] -->|同步调用| G[Native/UI线程<br>Fabric同步增量渲染]F -->|按需加载| H[TurboModules<br>使用时懒初始化]endOldArch -->|架构演进| NewArch

在这里插入图片描述
在这里插入图片描述

🔍 新旧架构核心区别解析

该演进主要是为了克服 Bridge 存在的性能瓶颈和开发体验问题。

特性维度旧架构 (Bridge)新架构 (JSI + Fabric + TurboModules)
通信机制通过 Bridge 进行异步JSON 序列化/反序列化,开销大,延迟高(常超过3ms)。通过 JSI (JavaScript Interface) 实现 同步直接调用无序列化开销,延迟降至微秒级
线程模型三线程模型(JS, Native/UI, Shadow),线程间依赖 Bridge 通信,切换频繁,复杂易延迟。线程简化JS 线程与 UI 线程可直接通信(通过JSI),移除了独立的 Shadow 线程,减少了线程切换开销。
渲染系统异步“瀑布流”渲染:UI更新指令需通过Bridge顺序传递,易导致卡顿,尤其在高频操作(如列表滚动)时。Fabric 渲染器支持同步增量渲染,允许并发更新优先级调度,大幅提升列表流畅度和交互响应速度。
原生模块加载启动时全量初始化所有模块,无论其是否会被使用,拖慢启动速度,增加内存占用。TurboModules 支持按需懒加载,模块仅在首次被调用时初始化,显著优化启动时间和内存使用。
类型安全与开发手动编写桥接代码,类型不安全,调试困难,容易出错。Codegen 在构建时自动生成类型安全的绑定代码,减少手动工作量,提升开发效率和代码可靠性。
向后兼容与迁移-新架构支持逐步迁移,提供了兼容层,但旧模块需重构以适应新的通信机制(JSI)。

💡 架构演进的主要原因

  1. 突破性能瓶颈:旧架构的异步序列化通信(Bridge)和线程模型是主要性能瓶颈,无法满足复杂应用(如高频交互、大型列表)对流畅性的要求。新架构的 JSI(直接同步调用)Fabric(同步渲染) 从根本上解决了这些问题。
  2. 提升开发体验:旧架构下,原生模块的开发调试复杂。新架构通过 Codegen 自动生成类型安全的代码,并集成了更好的调试工具支持,简化了开发流程。
  3. 优化资源利用:旧架构启动时初始化所有原生模块的方式浪费资源。新架构的 TurboModules 实现了按需加载,提升了启动速度和内存利用效率。
  4. 为未来特性做准备:新架构引入了 并发渲染 等能力,为支持 React 18 及更现代的并发特性(如 Suspense、Transitions)奠定了基础,使应用能更好地处理异步任务和优先级调度。

📊 性能提升对比

性能指标旧架构 (Bridge)新架构 (JSI + Fabric)提升幅度
通信延迟> 3ms (高)< 0.1ms (极低)数十倍
列表渲染速度120ms (慢,易卡顿)50ms (快,流畅)约 60%
启动时间长 (全模块初始化)短 (按需加载)减少 30%
内存占用高 (多份数据拷贝)低 (共享内存)显著优化

🛠 给开发者的建议

  • 新项目:应直接采用新架构(React Native 0.68+ 版本默认开启),并充分利用 Hermes 引擎FabricTurboModules 带来的性能优势。
  • 现有项目迁移:建议逐步迁移
    1. 确保所有原生模块适配 TurboModules 规范
    2. 逐步替换依赖 Bridge 的第三方库。
    3. 启用 Hermes 引擎和 Codegen
  • 学习重点:掌握 JSI 的直接通信原理Fabric 的渲染流程 以及如何利用 Codegen 生成类型安全的接口

💎 总结

React Native 的架构演进是从 “能用”到“好用” 的重大飞跃。新架构通过 JSIFabricTurboModules 三大支柱,彻底解决了旧架构在性能开发体验资源利用上的核心痛点,使其更适用于开发高性能、用户体验接近原生的复杂应用。


好的,我将为你详细介绍React Native的架构演进过程及其原因,撰写一篇易于理解的博客。主要内容如下:

  • React Native简介:介绍React Native的基本概念和架构演进的重要性。
  • 旧架构:Bridge模式:使用比喻和代码示例说明旧架构的工作原理和瓶颈。
  • 新架构核心革新:详细分析JSI、Fabric、TurboModules三大支柱的技术原理和优势。
  • 架构演进原因:从性能、开发体验、维护性等角度分析架构升级的驱动力。
  • 总结与展望:对比架构变化的价值,展望未来发展方向。

接下来,我将开始撰写博客正文:


React Native架构演进:从Bridge到JSI、Fabric的革命性升级

1 引言:什么是React Native及其架构演进的重要性

React Native自2015年由Facebook推出以来,一直秉承着"Learn Once, Write Everywhere"的理念,旨在让开发者能够使用JavaScript和React来开发真正原生的移动应用。它不同于Hybrid应用(如Cordova)和WebView渲染,而是直接调用原生UI组件进行渲染,既保留了React的开发体验,又提供了接近原生的性能表现。

然而,任何技术都需要随着时代的发展而不断演进。React Native的初始架构虽然简单易用,但随着应用复杂度的增加和用户对性能要求的提高,逐渐暴露了一些瓶颈问题。经过多年的开发和探索,React Native团队推出了以JSI、Fabric和TurboModules为代表的新架构,这不仅是技术栈的升级,更是设计理念的飞跃,从根本上重构了JavaScript与原生代码之间的通信和协作方式。

理解这一架构演进过程,不仅有助于我们更好地使用React Native开发现代应用,也能让我们洞察移动应用开发技术的发展趋势。本文将深入浅出地介绍React Native从旧架构到新架构的演进过程、原因以及新架构带来的优势。

2 旧架构:Bridge模式的工作原理与瓶颈

2.1 桥接机制的形象比喻

在React Native的旧架构中,最核心的概念是Bridge(桥接器)。你可以把它想象成两个语言不同的国家(JavaScript世界和原生世界)之间的翻译官。所有对话都需要经过这个翻译官进行转换和传递:

  • JavaScript国度:运行你的React代码和业务逻辑,使用JavaScriptCore或Hermes引擎执行
  • 原生国度:包括iOS(Objective-C/Swift)和Android(Java/Kotlin)平台,负责渲染UI和调用设备能力
  • 翻译官(Bridge):在两国之间传递消息,需要将每种语言翻译成对方能理解的形式

2.2 三线程模型与通信流程

旧架构依赖于三层线程模型来实现跨平台交互:

  1. JS线程:执行JavaScript代码和React渲染逻辑,计算UI变化
  2. 原生/UI线程:处理原生渲染和用户交互,是唯一能操作UI的线程
  3. Shadow线程:使用Yoga引擎计算布局,确定UI元素的精确位置和大小

当需要更新UI时,通信流程如下:

// JS线程发起调用
NativeModules.CalcModule.add(2, 3, (result) => console.log(result));// 背后实际发生的过程:
// 1. 序列化:将调用信息转为JSON字符串
// { module: 'CalcModule', method: 'add', args: [2,3], callbackId: 123 }
// 2. 通过Bridge传递到原生线程
// 3. 反序列化:原生端解析JSON,执行真正的方法
// 4. 结果再次序列化,通过Bridge返回JS线程
// 5. JS线程反序列化结果,执行回调函数

2.3 旧架构的瓶颈与限制

尽管Bridge设计简单易懂,但随着应用复杂度的增加,它逐渐暴露出若干严重问题:

  • 序列化开销巨大:所有数据都需要序列化为JSON字符串,复杂对象和大型数组的处理成本很高,估计70%的通信时间花在序列化/反序列化上。
  • 异步通信延迟:由于通信必须是异步的,JS线程无法同步获取原生端的信息(如组件尺寸),导致交互响应延迟可达100ms+
  • 内存使用效率低:通信过程中产生的临时JSON字符串占用大量内存,且很快成为需要回收的垃圾。
  • 线程切换频繁:多线程模型导致线程间切换频繁,进一步增加了性能开销。
  • 启动性能差:所有原生模块都需要在启动时初始化,即使某些模块永远不会被使用。

这些瓶颈在复杂应用尤其是需要高频交互(如动画、手势、列表滚动)的场景中变得尤为明显,促使React Native团队重新思考整个架构设计。

3 新架构核心革新:JSI、Fabric与TurboModules

为了解决旧架构的性能瓶颈,React Native团队推出了新架构,围绕三大核心支柱构建:JSI(JavaScript接口)、Fabric渲染系统和TurboModules。

3.1 JSI(JavaScript Interface):通信的革命

JSI是新架构的基石,它彻底改变了JavaScript与原生代码之间的通信方式。

3.1.1 从"传纸条"到"直接通话"

与Bridge模式的"传纸条"方式不同,JSI更像是为JavaScript和原生代码之间建立了直接电话线路,允许双方直接对话:

  • 直接内存访问:JavaScript可以直接持有和操作C++对象(Host Objects),无需序列化
  • 同步调用能力:支持同步方法调用,大大减少了通信延迟
  • 引擎无关性:JSI是抽象接口,可以适配不同JavaScript引擎(Hermes、JavaScriptCore等)
// JSI允许JavaScript直接调用C++对象方法
jsi::Function::createFromHostFunction(runtime, jsi::PropNameID::forAscii(runtime, "nativeMethod"),2,jsi::Runtime& rt, const jsi::Value& thisVal, const jsi::Value* args, size_t count {// 直接调用原生方法,无需序列化nativeModule->method(args[0].asString(rt).utf8(rt));return jsi::Value::undefined();}
);
3.1.2 性能提升显著

JSI带来的性能提升是显著的:方法调用延迟从10-50ms降至1ms以下,内存占用减少30-50%,动画帧率提升2倍,启动时间优化40-60%。

3.2 Fabric:渲染系统的重构

Fabric是新的渲染系统,旨在解决旧架构中UI渲染的瓶颈问题。

3.2.1 同步渲染能力

传统的异步渲染模式导致UI更新需要经历多个线程和序列化过程,而Fabric引入了同步渲染机制

  • 直接控制:JavaScript可以直接控制原生渲染树,减少通信层级
  • 优先级调度:支持并发渲染,高优先级更新(如用户交互)可以中断低优先级任务
  • 增量渲染:只更新发生变化的部分,减少不必要的重渲染
3.2.2 线程模型简化

Fabric简化了线程模型,移除了Shadow线程,将布局计算等功能整合到跨线程的C++核心中,减少了线程切换和同步开销。

3.2.3 性能对比

以下是Fabric与旧渲染系统的性能对比:

性能指标旧渲染系统Fabric提升幅度
列表滚动流畅度易卡顿,丢帧率高流畅,接近原生40%以上
内存使用高(多线程+序列化)低(共享内存)30-50%
渲染延迟高(异步多线程)低(同步直连)10-20倍

3.3 TurboModules:模块系统的优化

TurboModules重新设计了原生模块的加载和调用方式,解决了旧架构中模块系统的性能问题。

3.3.1 按需加载机制

与旧架构在启动时初始化所有模块不同,TurboModules采用懒加载策略:模块只有在首次被JavaScript代码引用时才会初始化,显著减少了启动时间和内存占用。

3.3.2 类型安全接口

通过Codegen工具,TurboModules可以根据TypeScript或Flow类型定义自动生成类型安全的绑定代码,减少了手动编写桥接代码的工作量,同时提高了类型安全性。

// Codegen根据类型定义自动生成绑定代码
interface Spec extends TurboModule {+getConstants: () => {};+add: (a: number, b: number) => number;
}export default TurboModuleRegistry.getEnforcing<Spec>('SampleTurboModule');
3.3.3 直接调用优化

通过JSI,JavaScript可以直接调用TurboModules中的方法,避免了Bridge的序列化和异步排队开销,方法调用性能提升显著。

4 架构演进的原因与驱动力

React Native架构演进并非一时兴起,而是由多方面因素共同推动的必然结果。

4.1 性能瓶颈的突破需求

旧架构的性能瓶颈在实际应用中变得越来越明显,特别是在复杂场景下:

  • 高频交互场景:如视频编辑、游戏、AR应用等需要高频JavaScript与原生通信的场景,Bridge的延迟成为致命问题
  • 复杂UI界面:长列表、复杂动画等需要频繁UI更新的场景,异步渲染导致卡顿和掉帧
  • 启动性能:随着应用规模增大,启动时初始化所有模块的方式导致启动时间越来越长

这些性能问题限制了React Native在高性能需求场景中的应用,推动了新架构的开发。

4.2 开发体验的提升需求

除了性能考虑,开发体验也是架构演进的重要驱动力:

  • 类型安全:JavaScript的动态类型特性在大型项目中难以维护,需要更强的类型保障
  • 调试体验:旧架构中Bridge通信的黑盒特性使调试变得困难,需要更透明的调试体验
  • 开发效率:手动编写桥接代码和类型定义效率低下,需要自动化工具支持

新架构通过Codegen等技术解决了这些问题,显著提升了开发体验。

4.3 技术债务的清理与未来准备

旧架构在设计之初存在一些技术债务,如:

  • 复杂的线程模型:多线程模型增加了复杂性和不可预测性
  • Bridge的单点故障:Bridge成为系统瓶颈和单点故障源
  • 扩展性限制:旧架构难以支持更复杂的功能和更好的性能优化

新架构通过重构解决了这些技术债务,同时为未来功能(如WebAssembly、服务器端渲染等)做好了准备。

4.4 生态系统的发展需求

随着React Native生态系统的发展,需要更灵活的架构支持:

  • 多引擎支持:旧架构与JavaScriptCore紧密耦合,难以支持其他引擎
  • 跨平台一致性:需要更好的跨平台一致性,减少iOS和Android之间的差异
  • 第三方库支持:需要为第三方库提供更高效的集成方式

新架构通过JSI的引擎无关性和TurboModules的跨平台一致性解决了这些问题。

5 总结与展望

React Native的架构演进是从"能用"到"好用"的重要飞跃,解决了旧架构的核心瓶颈问题,为未来发展奠定了坚实基础。

5.1 架构演进的价值总结

下表总结了React Native架构演进的主要价值:

方面旧架构(Bridge)新架构(JSI+Fabric+TurboModules)
通信方式异步JSON序列化直接同步调用
渲染性能异步易卡顿同步流畅渲染
内存使用高(序列化开销)低(共享内存)
启动时间长(全量初始化)短(按需加载)
开发体验手动桥接,类型不安全自动生成,类型安全
扩展性有限强大(支持未来功能)

5.2 实际应用中的影响

对于开发者而言,新架构带来以下实际好处:

  • 更流畅的用户体验:特别是动画和交互密集型应用
  • 更快的启动速度:模块懒加载显著减少启动时间
  • 更低的内存占用:减少序列化开销和内存拷贝
  • 更好的开发体验:类型安全和自动化代码生成
  • 更简单的线程模型:减少多线程编程的复杂性

5.3 未来发展方向

React Native架构演进仍在继续,未来可能的发展方向包括:

  • 更深入的原生集成:进一步缩小与原生开发的性能差距
  • 更多并发特性:更好地利用多核处理器能力
  • WebAssembly支持:支持高性能计算场景
  • 服务器端渲染:支持服务端组件等新特性
  • AR/VR支持:适配新兴的AR/VR平台和设备

5.4 迁移建议

对于现有项目,迁移到新架构需要一定工作量,但通常是值得的:

  1. 评估需求:如果应用遇到性能瓶颈或需要新特性,考虑迁移
  2. 逐步迁移:可以逐步启用新架构特性,不必一次性完全迁移
  3. 测试验证:迁移前后进行性能测试,验证改进效果
  4. 关注生态:确保依赖的第三方库支持新架构

React Native的架构演进体现了技术发展的必然规律:从简单到复杂,再从复杂到高效。新架构为解决性能瓶颈和开发体验问题提供了强大基础,为React Native的未来发展打开了新的可能性。


React Native 从旧架构(基于 Bridge)演进到新架构(基于 JSI、Fabric、TurboModules),是一次根本性的重构,旨在解决性能瓶颈和开发体验问题。下面我将为你梳理它们的核心区别。

特性维度旧架构 (Bridge)新架构 (JSI + Fabric + TurboModules)
通信机制异步 Bridge,JSON 序列化 📨JSI 直接同步调用 ⚡
线程模型三线程(JS, Shadow, UI)🔗简化线程,直接交互 🔄
渲染系统异步瀑布流,易阻塞 🐢同步增量渲染,支持并发 🚀
模块加载启动时全量初始化 ⏳按需懒加载 🎯
类型安全手动桥接,易出错 ❌Codegen 自动生成,类型安全 ✅
开发体验调试困难,性能优化复杂 🥊工具集成完善,调试更清晰 🔧

🔄 一、通信机制:从“传纸条”到“直接通话”

  • 旧架构 (Bridge)
    像个中间人信使。JS 和 Native 世界不能直接交谈,所有通信都必须通过一个叫 Bridge 的通道。消息(指令、数据)需要被序列化成 JSON 字符串,通过 Bridge 异步传递,另一边接收后再反序列化回原始格式。这个过程就像两个房间的人靠传纸条沟通,慢且开销大,是高延迟和性能瓶颈的主要根源。

  • 新架构 (JSI)
    JSI (JavaScript Interface) 彻底取消了“中间人”。它允许 JavaScript 直接持有并调用 C++ 对象(Host Objects)的方法,实现了同步或异步的直接通信。这就像两个房间的人装上了内部电话,可以直接对话,甚至能直接操作对方房间里的东西,速度极快,几乎没有延迟


🧵 二、线程模型:从“三线程协作”到“精简高效”

  • 旧架构
    依赖三个线程

    1. JS 线程:执行 JavaScript 代码和业务逻辑。
    2. Shadow 线程:专门用于计算布局(Yoga 引擎)。
    3. UI 线程(主线程):负责原生组件的渲染和用户交互。
      它们通过 Bridge 进行异步通信,频繁的线程切换和序列化操作带来了显著性能开销。
  • 新架构
    线程模型大幅简化Shadow 线程被移除,其布局计算等功能被整合到一个跨线程的 C++ 核心中。JS 线程通过 JSI 可以直接与 UI 线程通信,减少了线程切换次数,使交互更加流畅。


🎨 三、渲染系统:从“批量更新”到“增量并发”

  • 旧架构
    渲染是异步和批处理的。UI 更新指令需要在多个线程间顺序传递,像瀑布一样(瀑布流渲染)。这容易导致阻塞,在快速滚动列表或复杂动画时易出现卡顿和掉帧

  • 新架构 (Fabric)
    Fabric 是新的渲染器。它允许 JavaScript 直接控制 Shadow Tree(布局树),并支持增量渲染并发更新。这意味着 UI 更新可以同步发生,高优先级的交互(如手势)可以中断低优先级的渲染,从而提供更流畅的体验(接近 60 FPS) 和更好的响应性。


📦 四、原生模块:从“启动全加载”到“按需加载”

  • 旧架构
    所有 Native Modules 都必须在应用启动时全部初始化,无论它们是否会被立刻用到。这会拖慢启动速度并增加内存占用。

  • 新架构 (TurboModules)
    TurboModules 引入了按需懒加载机制。一个原生模块只有在 JavaScript 端首次真正调用它时才会被初始化。这显著减少了启动时间,降低了内存开销。


🛟 五、类型安全与开发体验

  • 旧架构
    在 JS 和 Native 间传递数据和调用方法时,类型是不安全的。需要手动编写桥接代码,容易因参数类型不匹配导致运行时错误,调试起来也比较困难。

  • 新架构 (Codegen)
    Codegen 是一个关键工具。你可以通过类型定义文件(如 TypeScript 或 Flow)定义接口,Codegen 会在构建时自动生成跨 JS 和 Native 的类型安全的绑定代码。这大大减少了手动编写桥接代码的工作量,并避免了运行时类型错误,提升了开发效率和代码可靠性。


💎 总结

React Native 的新架构通过 JSI、Fabric、TurboModulesCodegen 的协同工作,解决了旧架构在性能、开发体验和类型安全方面的核心痛点。

  • 如果你要开发新项目,强烈推荐基于新架构进行。
  • 如果你要优化现有项目,评估迁移成本后,逐步向新架构迁移是提升应用性能的有效途径。

希望这些信息能帮助你更好地理解 React Native 的架构演进!


文章转载自:

http://hQNWOVus.Lmxzw.cn
http://O93cVkb1.Lmxzw.cn
http://Dw2MyEuU.Lmxzw.cn
http://FqqlHqe7.Lmxzw.cn
http://mhUDClfJ.Lmxzw.cn
http://QDFc1vNX.Lmxzw.cn
http://6zlsWr8d.Lmxzw.cn
http://un6NeHI1.Lmxzw.cn
http://fb24k2oi.Lmxzw.cn
http://tvrwlzsz.Lmxzw.cn
http://xoCkwRB2.Lmxzw.cn
http://lJXbV6Gq.Lmxzw.cn
http://VJhulvzc.Lmxzw.cn
http://Ttywezw1.Lmxzw.cn
http://w5hqQqDz.Lmxzw.cn
http://EUgtZ0sf.Lmxzw.cn
http://aBawRSnm.Lmxzw.cn
http://X9otpoV6.Lmxzw.cn
http://gIFHdNkw.Lmxzw.cn
http://7h14cp2w.Lmxzw.cn
http://DPCAKkLK.Lmxzw.cn
http://pMm66Bu1.Lmxzw.cn
http://vLWIGW6X.Lmxzw.cn
http://5hjvaM4C.Lmxzw.cn
http://DYAZja6S.Lmxzw.cn
http://HrDFvCNj.Lmxzw.cn
http://JchNFwKf.Lmxzw.cn
http://6lubIbRA.Lmxzw.cn
http://AZFCmBDV.Lmxzw.cn
http://wS8ATxBs.Lmxzw.cn
http://www.dtcms.com/a/383101.html

相关文章:

  • Qt---描述网络请求QNetworkRequest
  • XLua教程之Lua调用C#
  • 第七章:AI进阶之------条件语句(if-elif-else)(一)
  • 从希格斯玻色子到QPU:C++在高能物理与量子计算领域的跨界征程与深度融合
  • 二、vue3后台项目系列——安装相关依赖、项目常用辅助开发工具
  • Knockout.js 备忘录模块详解
  • VS2022下载+海康SDK环境配置实现实时预览
  • 前端基础 —— C / JavaScript基础语法
  • 手搓一个 DELL EMC Unity存储系统健康检查清单
  • 字节M3-Agent:如何实现一个支持多模态长期记忆与推理的Agent
  • TCL华星计划投建第8.6代印刷OLED产线
  • Qt学习:moc生成的元对象信息
  • Java—JDBC 和数据库连接池
  • 软件工程实践四:MyBatis-Plus 教程(连接、分页、查询)
  • 用 Go 快速上手 Protocol Buffers
  • Java Stream 流学习笔记
  • Linux线程id与简易封装线程实现
  • 公链分析报告 - Secret Network
  • JavaScript 简单链表题目试析
  • 【ZYNQ开发篇】Petalinux和电脑端的静态ip地址配置
  • 电商AI导购系统的模型部署架构:TensorFlow Serving在实时推荐中的实践
  • 光射三缝实验
  • K8s部署 Redis 主从集群
  • Android点击桌面图库应用启动流程trace分析
  • 【抗量子安全】全球视角下 PQC 与 QKD 技术洞察:政策引领与产业演进
  • 代码随想录学习摘抄day9(回溯1-11)
  • 数据处理指令
  • SpringBoot 中 ZK 与 Kafka 节点选择逻辑:底层原理与实践解析
  • 事务与mysql数据库锁的关系
  • 继承类模板:函数未在模板定义上下文中声明,只能通过实例化上下文中参数相关的查找找到