ohos_napi_rs:基于 OpenHarmony 的 ArkTS 与 Rust 通信框架项目

可用于 OpenHarmony 应用中实现 ArkTS 与 Rust 的相互调用,尤其适用于游戏、物理模拟等对性能有要求的场景。核心功能包括数据类型转换、函数注册,通过过程宏简化开发,提升交互效率。【此简介由AI生成】

分支1Tags1

OHOS_NAPI_RS

简介

ohos_napi_rs(forked from napi-rs)是一个用于实现ArkTS和Rust通信的框架。为用户提供了ArkTS和Rust相互调用的能力。

图 1 ohos_napi_rs在 OpenHarmony 中的位置

structure

一般情况下OpenHarmony应用开发使用ArkTS/JS语言,但部分场景由于性能、效率等要求,比如游戏、物理模拟等,需要依赖使用现有的C/C++库。

ohos_napi_rs为开发者提供ArkTS和Rust模块之间的交互能力。包括ArkTS和Rust数据类型转换、函数相互调用的能力。

  • ArkTS:OpenHarmony应用开发语言;
  • ArkTS Native Module(Rust):使用Rust开发的native模块;
  • ArkTS Native Module(C++):使用C++开发的native模块;
  • ohos_napi_rs:提供ArkTS和Rust交互能力;
  • Node-API:napi接口,实现ArkTS和C/C++交互能力;

图 2 ohos_napi_rs 内部架构图

runtime_framework

ohos_napi_rs 内部主要分为三个模块:

  • Rust sys:使用Rust CFFI封装底层napi接口;
  • Rust napi:实现Rust数据类型和ArkTS数据类型相互转换;提供Rust函数注册进ArkTS的逻辑;
  • Rust macro:提供用户使用的过程宏,如#[napi],自动完成ArkTS和Rust数据类型转换、Rust函数注册功能;

目录

ohos_napi_rs
├── crates
│   ├── backend
│   │   └── src                     # 过程宏底层实现逻辑
│   │       ├── codegen             # 过程宏自动生成类型转换、函数注册代码
│   │       └── typegen             # 过程宏自动生成ArkT函数头文件逻辑(d.ts)
│   ├── build
│   │   └── src                     # 编译脚本
│   ├── macro
│   │   └── src                     # 过程宏对外接口实现
│   │       ├── expand              # 过程宏对外接口
│   │       └── parser              # 过程宏TokenStream解析
│   ├── napi
│   │   └── src
│   │       ├── bindgen_runtime     # Rust函数注册、类型转换
│   │       │   └── js_values       # Rust原生数据类型和ArkTS类型转换逻辑实现,如Rust(String)对应ArkTS(string)
│   │       └── js_values	        # Rust安全引用类型和ArkTS类型转换逻辑实现	,如Rust(JsString)对应ArkTS(string)			
│   │           └── string 			# Rust String类型,如latin1、utf16、utf8
│   └── sys
│       └── src						# Rust CFFI封装底层napi接口
├── docs                            # 使用文档
└── figures                         # 架构图

编译构建

使用Cargo编译

  1. 环境准备,安装Rust和ohos-sdk。

    Rust需要保证版本 >= 1.78.0,并且安装OpenHarmony对应的toolchain。

    rustup target add aarch64-unknown-linux-ohos
    rustup target add armv7-unknown-linux-ohos
    rustup target add x86_64-unknown-linux-ohos
    

    ohos-sdk可以从每日构建获取,ohos-sdk中包含native库和编译工具链。

  2. 新建Rust工程,在 Cargo.toml 中引入 ohos_napi_rs,设置Rust输出库类型为cdylib。

    [dependencies]
    napi = {path = "ohos_napi_rs/crates/napi"}
    napi-derive = {path = "ohos_napi_rs/crates/macro"}
    
    [build-dependencies]
    napi-build = {path = "ohos_napi_rs/crates/build"}
    
    [lib]
    crate-type=["cdylib"]
    
  3. 添加Rust构建脚本build.rs。

    // build.rs
    fn main() {
      napi_build::setup();
    }
    
  4. 开发Rust代码。

    use napi_derive::napi;
    
    #[napi]
    fn add(a: u32, b: u32) -> u32 {
      a + b
    }
    
  5. 设置Rust构建时使用的linker,在工程项目中新建.cargo/config.toml文件。

    参考Rust官方文档

    [target.x86_64-unknown-linux-ohos]
    linker = "/path/to/x86_64-unknown-linux-ohos-clang.sh"
    
    [target.armv7-unknown-linux-ohos]
    linker = "/path/to/armv7-unknown-linux-ohos-clang.sh"
    
    [target.aarch64-unknown-linux-ohos]
    linker = "/path/to/aarch64-unknown-linux-ohos-clang.sh"
    

    创建以下shell脚本,从ohos-sdk中封装编译工具链:

    x86_64-unknown-linux-ohos-clang.sh:

    #!/bin/sh
    exec /path/to/ohos-sdk/linux/native/llvm/bin/clang \
      -target x86_64-linux-ohos \
      --sysroot=/path/to/ohos-sdk/linux/native/sysroot \
      -Wl --no-undefined \
      -D__MUSL__ \
      "$@"
    

    armv7-unknown-linux-ohos:

    #!/bin/sh
    exec /path/to/ohos-sdk/linux/native/llvm/bin/clang \
      -target arm-linux-ohos \
      --sysroot=/path/to/ohos-sdk/linux/native/sysroot \
      -Wl --no-undefined \
      -D__MUSL__ \
      -march=armv7-a \
      -mfloat-abi=softfp \
      -mtune=generic-armv7-a \
      -mthumb \
      "$@"
    

    aarch64-unknown-linux-ohos-clang.sh:

    #!/bin/sh
    exec /path/to/ohos-sdk/linux/native/llvm/bin/clang \
      -target aarch64-linux-ohos \
      --sysroot=/path/to/ohos-sdk/linux/native/sysroot \
      -Wl --no-undefined \
      -D__MUSL__ \
      "$@"
    

    使用cargo命令进行编译:

    cargo build --target x86_64-unknown-linux-ohos --release
    cargo build --target armv7-unknown-linux-ohos --release
    cargo build --target aarch64-unknown-linux-ohos --release
    
  6. 将Rust编译生成的so以预构建库的方式添加到ArkTS工程中,添加到以下对应平台的目录中,如果没有文件夹就新建。

    arktsProject/entry/libs/arm64-v8a
    arktsProject/entry/libs/armeabi-v7a
    arktsProject/entry/libs/x86_64
    

    在arkts工程中添加头文件声明,并调用Rust函数。

    index.d.ts

    export declare function add(a: number, b: number): number;
    

    Index.ets

    import rustNapi from 'libarkts_napi_sdv.so';
    
    let res: number = rustNapi.add(2, 4);
    expect(res).assertEqual(6);
    

用户指南

详细内容请见用户指南

致谢

本库基于napi-rs仓库进行适配,完成ArkTS和Rust的互通功能。同时也参考了ohos-rs的实现设计,在此对napi-rs和ohos-rs表示感谢。

项目介绍

可用于 OpenHarmony 应用中实现 ArkTS 与 Rust 的相互调用,尤其适用于游戏、物理模拟等对性能有要求的场景。核心功能包括数据类型转换、函数注册,通过过程宏简化开发,提升交互效率。【此简介由AI生成】

定制我的领域