React Native 应用鸿蒙化改造的核心目标,是在尽量保留既有 JS 业务逻辑和 React 组件结构的前提下,为 HarmonyOS 补齐 Native 工程、依赖、打包、运行和调试链路。实际落地时,不建议把它理解成一次简单的“换平台编译”,而是一次从工程结构到运行容器的完整接入。

本文按实践顺序梳理关键步骤,帮助已有 RN 项目完成 HarmonyOS 侧接入。

一、先确认改造边界

开始前先明确三件事:

  • JS 层业务逻辑是否可以复用。
  • Native 能力是否依赖大量 Android 或 iOS 专属模块。
  • 项目当前 RN 版本是否与 RNOH 目标版本匹配。

如果项目主要由 React 组件、JS 状态管理、网络请求和通用业务逻辑组成,迁移成本通常集中在工程接入、依赖适配和少量 Native 能力补齐上。如果项目深度依赖原生 SDK,则需要提前盘点这些 SDK 是否已有 HarmonyOS 版本,或者是否需要用 ArkTS / C++ 自行封装。

二、准备 HarmonyOS 工程

推荐在原 RN 项目中新增 harmony 目录,作为 HarmonyOS Native 工程入口。这样可以让 JS 业务代码继续留在原工程中,同时把平台侧工程隔离出来。

典型结构如下:

project
├── src
├── package.json
├── index.js
├── metro.config.js
└── harmony
    ├── AppScope
    ├── entry
    ├── build-profile.json5
    ├── hvigorfile.ts
    └── oh-package.json5

其中 harmony/entry 是主模块,负责创建 Ability、加载 RN 页面、承载 RNOH 运行时。JS 入口仍然由 Metro bundle 提供。

三、安装 RNOH 依赖

HarmonyOS 侧需要通过 ohpm 安装 RNOH 相关依赖。一般会包含 RNOH runtime、接口包以及项目需要的三方库适配包。

安装后重点检查:

  • oh-package.json5 中依赖版本是否和项目 RN 版本匹配。
  • build-profile.json5 中签名、模块、target 信息是否完整。
  • DevEco Studio 是否能正确同步工程。

这里不要混用不匹配的 RNOH 版本。RN、RNOH、HarmonyOS SDK 三者版本错位时,常见表现是编译通过但运行期 TurboModule、Fabric 或 bundle 加载异常。

四、配置 bundle 构建

RN 的 JS bundle 仍然由 Metro 产出。HarmonyOS 侧需要能找到这个 bundle,并在运行时加载。

常见做法是新增脚本:

{
  "scripts": {
    "bundle:harmony": "react-native bundle --platform harmony --dev false --entry-file index.js --bundle-output harmony/entry/src/main/resources/rawfile/index.bundle --assets-dest harmony/entry/src/main/resources/rawfile"
  }
}

实际命令要根据项目目录和 RNOH 版本调整。关键点是:

  • bundle 输出到 HarmonyOS 工程可访问的资源目录。
  • 图片等 assets 同步输出。
  • entry file 与原 RN 项目保持一致。

如果 bundle 路径配置错误,运行时通常会出现页面空白、bundle load failed 或 JS 入口找不到的问题。

五、接入 RNInstance

HarmonyOS 侧需要创建 RNInstance,并将它绑定到页面容器。通常流程是:

  1. Ability 启动。
  2. 初始化 RNOH runtime。
  3. 创建 RNInstance。
  4. 指定 bundle 路径。
  5. 创建并挂载 RN 页面。

在 ArkTS 页面中,重点是把 RNOH 提供的容器组件放到正确位置,并保证生命周期能跟随 Ability 正常创建、前后台切换和销毁。

改造时不要只验证首屏能显示,还要验证:

  • 返回前台后 RN 页面是否正常恢复。
  • 页面销毁后是否释放 RNInstance。
  • 多页面场景是否会重复创建或错误复用实例。
  • 热更新或重新加载 bundle 时是否路径稳定。

六、适配 Native 能力

已有 RN 项目常见 Native 依赖包括:

  • 文件选择、相册、相机。
  • 设备信息、网络状态。
  • 定位、权限、推送。
  • 本地存储、加密、分享。
  • 自定义业务 SDK。

迁移时优先判断依赖是否已有 RNOH / HarmonyOS 适配版本。如果没有,需要按 TurboModule 或 NativeModule 方式补齐。

模块适配时要注意 name contract。JS 层 NativeModules.xxx 或 TurboModule registry 查找的名称,必须和 Native 侧注册名称一致。名称不一致时,JS 层表现通常是模块为 null 或方法不存在。

七、处理 UI 和交互差异

React 组件多数可以复用,但仍要检查平台差异:

  • Text、Image、ScrollView、FlatList 等基础组件的表现。
  • 手势、滚动、输入框、键盘弹起。
  • zIndex、overflow、透明色等渲染细节。
  • Safe area、状态栏、导航栏区域。
  • 字体、字号、行高和截断策略。

建议先跑核心页面,再跑表单、列表、弹窗、复杂嵌套滚动等高风险页面。不要只用 demo 页面判断迁移完成。

八、调试和验证

基础验证清单:

  • DevEco Studio 可以构建并安装 HAP。
  • 应用启动后能加载 bundle。
  • 首页和核心业务页面可正常渲染。
  • 路由跳转、返回、刷新正常。
  • 网络请求、登录态、错误提示正常。
  • 图片资源和本地 assets 能正确加载。
  • NativeModule / TurboModule 可调用。
  • release 包可以正常运行。

如果出现白屏,优先按顺序检查:

  1. bundle 是否生成。
  2. bundle 是否被打进资源目录。
  3. Native 侧 bundle 路径是否正确。
  4. JS 入口是否注册了正确 component name。
  5. RNOH runtime 初始化是否成功。
  6. 控制台是否有 JS exception。

九、常见问题

bundle 找不到

确认 bundle 输出路径、资源目录和 Native 加载路径一致。路径问题是最常见的首屏失败原因。

NativeModule 不存在

确认模块注册名称、JS 访问名称和 codegen 产物一致。不要只看文件存在,要看运行时 registry 是否能查到。

图片不显示

先区分网络图、本地 asset、打包资源三种来源。网络图检查 URL 和权限,本地 asset 检查 Metro assets 输出,资源图检查 HarmonyOS rawfile 路径。

release 可运行但 debug 异常

检查 bundle 模式、dev flag、Metro 服务和设备网络。debug 模式依赖开发服务,release 模式依赖本地 bundle。

页面显示但交互异常

优先检查手势、滚动容器、键盘和焦点。HarmonyOS 的输入、滚动和布局细节可能与 Android / iOS 不完全一致,需要逐页验证。

十、建议迁移节奏

推荐按下面节奏推进:

  1. 先让空页面跑通 RNOH。
  2. 接入真实 JS bundle。
  3. 跑通首页和路由。
  4. 逐个恢复核心页面。
  5. 处理 Native 能力。
  6. 做 release 包验证。
  7. 补齐崩溃、日志和回归测试。

不要一开始就把所有页面和 Native SDK 一次性接入。先把运行链路跑通,再逐层恢复能力,问题会更容易定位。

总结

RN 应用鸿蒙化改造的关键,不是简单复制工程模板,而是建立一条稳定的运行链路:JS bundle 能生成、HarmonyOS 工程能加载、RNOH runtime 能创建、页面能渲染、Native 能力能注册并调用。

只要先把工程结构、bundle 路径、RNInstance 生命周期和 NativeModule 注册关系理顺,后续页面和业务能力的迁移就可以按模块逐步推进。

Logo

开源鸿蒙跨平台开发社区汇聚开发者与厂商,共建“一次开发,多端部署”的开源生态,致力于降低跨端开发门槛,推动万物智联创新。

更多推荐