TurboModule原理

如果你说的是 React Native New Architecture 里的 TurboModule,可以把它理解成:

TurboModule = React Native 用 JSI 把 JS 与原生模块连接起来的一套新机制。

它主要解决旧架构中 Bridge JSON 序列化 + 异步消息队列 带来的性能和类型安全问题。

1. 先看旧架构 Bridge

传统 RN:

javascript 复制代码
JavaScript
   │
   │  JSON / Message
   ▼
   Bridge
   │
   │  JSON / Message
   ▼
Native Module
   │
Android / iOS

例如:

scss 复制代码
NativeModules.UserModule.getUser(123)

实际上经历了类似:

arduino 复制代码
JS 调用
  ↓
参数序列化
  ↓
Bridge 消息队列
  ↓
Native 接收
  ↓
反序列化
  ↓
Java/Kotlin/Obj-C/Swift
  ↓
结果序列化
  ↓
Bridge
  ↓
JS

所以 Bridge 本质上是一个跨语言消息通信层。


2. TurboModule 的核心变化

TurboModule 配合 JSI(JavaScript Interface) :

javascript 复制代码
              JavaScript
                  │
                  │ JSI
                  ▼
          ┌───────────────┐
          │ TurboModule   │
          │    Binding    │
          └───────┬───────┘
                  │
        C++ / JNI / Obj-C++
                  │
          ┌───────┴───────┐
          ▼               ▼
       Android           iOS
       Kotlin/Java       Obj-C/Swift

关键区别:

以前:

arduino 复制代码
JS → JSON → Bridge → Native

现在:

复制代码
JS → JSI → Native

JSI 允许 JavaScript 引擎直接与 C++/Native 对象交互。


3. TurboModule 最核心的三个东西

可以记成:

复制代码
Spec
 ↓
Codegen
 ↓
TurboModule
 ↓
JSI
 ↓
Native

① Spec:定义接口

例如:

typescript 复制代码
export interface Spec extends TurboModule {
  getUser(id: number): Promise<User>;
}

你告诉 RN:

我有一个 Native Module,它有 getUser() 方法。


② Codegen:自动生成类型和绑定代码

New Architecture 非常重要的一点是:

JS 与 Native 之间的接口不是手写一套套胶水代码,而是通过 Codegen 生成。

例如:

csharp 复制代码
TypeScript Spec
      ↓
    Codegen
      ↓
┌───────────────┐
│ JS interface  │
│ C++ binding   │
│ Native types  │
└───────────────┘

这样可以减少:

  • 参数类型不一致
  • 手写 Bridge
  • 大量 boilerplate
  • JS / Native 接口漂移

4. 真正调用的时候发生什么?

假设:

ini 复制代码
const user = await UserModule.getUser(123);

大致过程:

scss 复制代码
JS
 │
 │ UserModule.getUser(123)
 ▼
JSI
 │
 ▼
TurboModule Binding
 │
 ▼
C++ / JNI / Obj-C++
 │
 ▼
Native Module
 │
 ▼
getUser(123)

返回:

javascript 复制代码
Native
  │
  ▼
Native result
  │
  ▼
JSI
  │
  ▼
JavaScript Promise

这里最重要的是:

TurboModule 并不是"JavaScript 直接调用 Java/Kotlin/Swift"。

中间仍然存在 Native Binding / JSI / C++ 等机制。


5. 为什么 JSI 很重要?

JSI 可以让 JS 持有一个 Native/C++ 对象的引用。

传统 Bridge 更像:

css 复制代码
JS:

{
  type: "CALL_MODULE",
  module: "Camera",
  method: "takePhoto",
  args: [...]
}

然后把这个消息扔给 Native。

而 JSI 更接近:

css 复制代码
JS Object
   │
   └──→ Native/C++ HostObject

JavaScript 调用:

scss 复制代码
camera.takePhoto()

最终可以进入 Native/C++ 实现。

所以它减少了传统 Bridge 中大量的:

复制代码
对象
 ↓
序列化
 ↓
传输
 ↓
反序列化

6. TurboModule 为什么叫 Turbo?

一个很重要的特性:

Lazy Loading

传统 Native Module 很多情况下会在启动阶段初始化:

复制代码
RN 启动
 ↓
初始化大量 Native Modules
 ↓
JS 开始执行

TurboModule 可以做到:

sql 复制代码
RN 启动
 ↓
只注册 Module
 ↓
JS 真正使用 UserModule
 ↓
才创建 UserModule

也就是:

复制代码
Register
   ↓
Lazy
   ↓
Instantiate

因此可以减少启动阶段不必要的初始化。


7. TurboModule 和 Fabric 是什么关系?

这是 RN New Architecture 非常容易混淆的一点。

sql 复制代码
              React Native New Architecture
                         │
             ┌───────────┴───────────┐
             ▼                       ▼
       TurboModule                  Fabric
             │                       │
       Native Modules          Native UI Components
             │                       │
       相机/定位/存储/etc          View/Text/Image

简单记:

技术 解决什么
JSI JS ↔ Native 的底层通信能力
TurboModule Native Module
Fabric Native UI / 渲染
Codegen JS ↔ Native 类型/接口生成
Hermes JavaScript Engine

所以:

TurboModule ≠ JSI

JSI 是底层能力,TurboModule 是建立在 JSI/Codegen 等机制上的 Native Module 架构。


8. 和旧 NativeModule 对比

javascript 复制代码
旧架构

JS
 │
 ▼
Bridge
 │
 ├── JSON Serialize
 ├── Message Queue
 └── JSON Deserialize
 │
 ▼
NativeModule

TurboModule:

复制代码
新架构

JS
 │
 ▼
JSI
 │
 ▼
TurboModule Binding
 │
 ▼
Native

核心收益:

① 减少 Bridge 通信开销

② 类型由 Codegen 保证

③ 支持 Lazy Loading

④ Native 对象可以通过 JSI 暴露

⑤ 更容易支持同步/高性能 Native 调用场景


9. 但是有一个非常重要的误区

不要简单理解成:

"TurboModule = 同步调用 Native,所以性能一定更高。"

并不是。

例如:

scss 复制代码
getUser(): Promise<User>

依然可以是异步的。

真正的变化是:

复制代码
通信机制

从:

arduino 复制代码
Message + Serialization + Bridge

变成:

复制代码
JSI + Native Binding

所以性能收益主要来自减少通信和序列化层的开销,而不是"所有 Native API 都变成同步"。


10. 面试时可以这样回答

如果面试官问:

TurboModule 原理是什么?

可以用这一套回答:

TurboModule 是 React Native New Architecture 中替代传统 NativeModule Bridge 的 Native Module 机制。它基于 JSI 和 Codegen,通过 TypeScript/Flow 定义 Native Module 的 Spec,再由 Codegen 生成 JS 与 Native 之间的类型和绑定代码。JS 调用 TurboModule 时,不再像旧架构一样通过 Bridge 将调用序列化成 JSON 消息,而是通过 JSI 进入 Native Binding,再调用具体的 Java/Kotlin 或 Objective-C/Swift 实现。同时 TurboModule 支持 Lazy Loading,可以在真正使用 Module 时再进行实例化,从而降低启动成本。

如果继续往底层追问:

javascript 复制代码
JS
 ↓
Hermes
 ↓
JSI
 ↓
HostObject / HostFunction
 ↓
TurboModule Binding
 ↓
C++ / JNI / Obj-C++
 ↓
Java/Kotlin / Obj-C/Swift

这条链路基本就是 TurboModule 原理的核心。

相关推荐
剪刀石头布啊5 小时前
vue-react为何要虚拟dom
前端
剪刀石头布啊5 小时前
ahooks常用的一些库,我们使用一下
前端
剪刀石头布啊5 小时前
从git更新本地提交记录到更新已经推送到远端记录
前端
Flynt7 小时前
axios 被投毒半年后,我把 npm 的"安全防线"实测了一遍:最信任的 SHA512 是安慰剂
前端·npm·node.js
excel8 小时前
Base62 和 Base64 有什么区别?
前端
风骏时光牛马9 小时前
大模型底层架构与AI源码深度剖析
前端
掘金挖土10 小时前
前端手摸手跑路之 AI 应用开发(九)
前端·后端
中文呀12 小时前
三维 GIS 离线缓存实战:逆向 CesiumOfflineCache,并亲手为它补上"自动更新"能力
前端
前进前进前进13 小时前
TRAE 全链路实战:做了一个警示牌一键生成器:纯 Canvas、单文件、零依赖
前端