【开源三方库】Aki:一行代码极简体验JSC++跨语言交互

开源项目 OpenHarmony

是每个人的 OpenHarmony

一、简介

OpenAtom OpenHarmony(以下简称“OpenHarmony”)的前端开发语言是ArkTS,在TypeScript(简称TS)生态基础上做了进一步扩展,继承了TS的所有特性,是JavaScript(简称JS)的超集。而Node-API(简称NAPI)是方舟引擎用于封装JS能力为Native插件的API,是前端JS与Native C/C++的FFI(Foreign Function Interface 跨语言交互接口)。

Aki——针对OpenHarmony上提供JS与C/C++跨语言互调的场景提供解决方案,提供了复杂度仅为O(1)级别的极简语法糖使用方式,一行代码完成JS与C/C++的无障碍跨语言互调,所键即所得。同时开发者无需关心NAPI的线程安全问题、Native对象GC问题,为开发者屏蔽NAPI内部复杂逻辑。

OpenHarmony中NAPI的用法不在本文阐述,不然就有点像孔乙己“茴香豆有几种写法”的感觉了。感兴趣的可以参考OpenHarmony关于Native API使用指导。而开发者使用NAPI过程中还会发现:为了做跨线程任务,需要做线程管理,需要关心环境上下文;为了使用结构体对象,需要关注napi_value生命周期如何管理;巴拉巴拉等等与自己业务无关的逻辑。搞了半天,发现业务代码一行没写,还在写NAPI的跨语言调用实现。拥有洁癖的开发者还会发现,很难做到隔离NAPI代码与业务代码,我们讨厌毫无边界性的编程

二、所键即所得:NAPI的尽头就是Aki

归根结底NAPI要做的就是FFI即跨语言调用,而开发者重视的是自己的业务逻辑而不是如何做跨语言调用:我就想把大象放进冰箱,你非要告诉我:先打开冰箱,然后抬起大象放进去,再关上冰箱。开发者想要的就是直截了当指明这个函数是个跨语言调用函数。Aki提供了JSBind语法糖,就做了这么一件事,开发者集成后,完全做到一行代码:所键即所得,并把业务代码与FFI代码完美隔离,提供了友好的边界性编程体验。

示例一:同步异步接口封装

示例一期望将C++业务逻辑(GetName)注册为JS同步接口(getSync)、异步接口(getAsync),Aki提供了极简的JSBind函数绑定语法糖,一行代码绑定跨语言调用接口:

● C/C++ Code

#include <aki/jsbind.h>// C++业务逻辑
std::string GetName(std::string key)
{
    std::string result = ...... // 获取数据的业务逻辑return result; // 返回字符串类型
}// Aki JSBind语法糖
JSBIND_ADDON(task_runner);
JSBIND_GLOBAL() {JSBIND_FUNCTION(GetName, "getNameSync"); // 绑定同步方法JSBIND_PFUNCTION(GetName, "getNameAsync"); // 绑定异步方法
}

● JavaScript Code


import libtask_runner from 'libtask_runner.so';const name = libstorage.getNameSync('name');// 调用同步方法
console.log('name is ' + name);// 调用异步方法
libstorage.getNameAsync('name').then(date => {
    console.log('name is ' + data);
}).catch(error => {
    console.log('error: ' + error);
});

示例二:Native与JS对象绑定

示例二期望将C++结构体/类对象(Person)逻辑注册为JS类对象(Person),包含类构造函数+类成员函数+类静态函数+类属性访问等特性,通知支持类对象作为参数及返回值。Aki提供了极简的JSBind对象绑定语法糖,开发者无需关注Native对象内存与JS引擎GC垃圾回收关系,直接绑定Native对象:

● C/C++ Code

#include <aki/jsbind.h>// C++逻辑
struct Person {// 构造函数,用于JS侧 new 对象Person(std::string name) : name(name) {}// 静态函数static Person GetAllPerson(); // 支持类对象作为参数// 成员函数int SayHello();    std::string name;
};// Aki JSBind语法糖
JSBIND_ADDON(person);
JSBIND_CLASS(Person) {JSBIND_CONSTRUCTOR<std::string>(); // 绑定构造函数JSBIND_METHOD(GetAllPerson); // 绑定类静态函数JSBIND_METHOD(SayHello); // 绑定类成员函数JSBIND_PROPERTY(name); // 绑定类成员属性
}

● JavaScript Code

import libperson from 'libperson.so';let person = new libperson.Person("aki"); // 调用构造函数
console.log('person name: ' + person.name); // 访问类属性
let greeting = person.SayHello(); // 调用类成员函数
let persons = libperson.Person.GetAllPerson(); // 调用类静态函数

示例三:在非JS线程中回调JS接口

示例三期望在非JS线程中回调JS接口,Aki提供了线程安全的JSBind语法糖,开发者无需关注JS线程安全问题——OpenHarmony方舟引擎规定JS回调的任务必须抛到JS线程中才能执行,否则会出现崩溃(即Native侧只能在JS线程使用NAPI)。

● C/C++ Code

#include <aki/jsbind.h>// C++逻辑
void SafetyCallback(std::function<void (std::string)> callback) {
    std::thread t([callback = std::move(callback)] () {callback("aki"); // 线程安全,直接调用});
    t.detach();
}// Aki JSBind语法糖
JSBIND_ADDON(sub_thread);
JSBIND_GLOBAL() {JSBIND_FUNCTION(SafetyCallback);
}

● JavaScript Code


import libsub_thread from 'libsub_thread.so';
// 入参为JS方法回调
libsub_thread.SafetyCallback((data) => {
  console.error('test result = ' + data); // test result = aki
})

示例四:Native调用绑定JS函数

示例四期望在C/C++侧调用JS接口(非回调)创建rdb关系型数据库表。Aki提供了JS侧的内建JSBind语法糖,开发者可直接绑定JS侧函数供Native侧调用。

● JavaScript Code


import libAddon from 'libaddon.so'function createTable(table: string) {
    rdbStore.executeSql()... // OHOS 关系型数据库逻辑
}libAddon.JSBind.bindFunction('createTable', createTable); // 绑定JS函数

● C/C++ Code


#include <aki/jsbind.h>// C++逻辑
bool DoSomethingFromNative() {if (auto createTable = aki::JSBind::GetJSFunction("createTable")) {
        createTable->Invoke<void>("MYSTORE"); // 入参类型 string}

示例五:类型转换

Aki支持丰富的类型转换,几乎所有JS的数据类型都可以通过Aki映射为同等的C/C++数据类型,开发者无需处理类型转换,如上述示例用法,框架支持自动匹配类型转换,下表为当前支持的完整类型转换关系:

三、集成依赖Aki

  1. 创建平台工程

DevEco Studio 创建包含Native C++的工程

File > New > Create Project | Module

  1. 配置依赖并安装

● ohpm三方组件依赖:@ohos/aki

指定模块路径下(如:项目根路径/entry),输入如下命令安装ohpm har包依赖:

cd entry
ohpm install @ohos/aki

CMakeLists.txt添加依赖:

...
set(AKI_ROOT_PATH ${CMAKE_CURRENT_SOURCE_DIR}/../../../oh_modules/@ohos/aki) # 设置AKI根路径
set(CMAKE_MODULE_PATH ${AKI_ROOT_PATH})
find_package(Aki REQUIRED)
...
target_link_libraries(${YOUR_TARGET} PUBLIC Aki::libjsbind) # 链接二进制依赖
...

● 源码依赖

用户自定义路径下(如:项目根路径/entry/src/main/cpp),输入如下命令下载源码:

cd entry/src/main/cpp
git clone https://gitee.com/openharmony-sig/aki.git

CMakeLists.txt添加依赖:

...
add_subdirectory(aki)
target_link_libraries(entry PUBLIC aki_jsbind) // entry 为编译目标
...

  1. 编译工程&运行

完成!!!

相关链接

《Aki使用指导》

OpenHarmony-SIG/aki

《Aki example》

OpenHarmony-SIG/aki - Gitee.com

OpenHarmony三方库中心仓

开放原子开源基金会三方库托管平台

DevEco Studio

HUAWEI DevEco Studio和SDK下载和升级 | HarmonyOS开发者

Native API使用指导

OpenAtom OpenHarmony

点击关注阅读原文,了解更多资讯

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/25775.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

SpringBoot开发环境热部署

目录 开发热部署 添加dev-tools依赖 在application.properties中配置devtools 在IDEA中添加设置 开发热部署 在实际的项目开发调试过程中会频繁地修改后台类文件&#xff0c;导致需要重新编译、 重新启动&#xff0c;整个过程非常麻烦&#xff0c;影响开发…

STM32 低功耗-待机模式

STM32 待机模式 文章目录 STM32 待机模式第1章 低功耗模式简介第2章 待机模式简介2.1 进入待机模式2.1 退出待机模式 第3章 待机模式代码部分总结 第1章 低功耗模式简介 在 STM32 的正常工作中&#xff0c;具有四种工作模式&#xff1a;运行、睡眠、停止和待机模式。 在系统或…

【Spring Cloud 六】Hystrix熔断

这里写目录标题 系列文章目录背景一、Hystrix是什么服务雪崩服务容错的相关概念熔断器降级超时控制限流 二、会什么要有Hystrix三、如何使用Hystrix进行熔断处理整体项目代码服务提供者pom文件yml配置文件启动类controller 服务消费者pom文件yml配置文件启动类feignhystrixcont…

信息安全技术工业控制系统安全控制应用指南学习笔记

工业控制系统安全控制基线 根据工业控制系统在国家安全、经济建设、社会生活中的重要程度&#xff0c;遭到破坏后对国家安全、社会秩序、公共利益以及公民、法人和其他组织的合法权益的危害程度等&#xff0c;结合信息安全等级保护标准划分及实施效果分析&#xff0c;结合工业…

前端主题切换方案——CSS变量

前言 主题切换是前端开发中老生常谈的问题&#xff0c;本文将介绍主流的前端主题切换实现方案——CSS变量 CSS变量 简介 编写CSS样式时&#xff0c;为了避免代码冗余&#xff0c;降低维护成本&#xff0c;一些CSS预编译工具&#xff08;Sass/Less/Stylus&#xff09;等都支…

JVM面试题

JVM理论 #JVM内存模型# Java内存模型&#xff08;JMM&#xff09;&#xff1f; Java的内存模型决定了线程间的通信方式&#xff0c;JMM的模型是由主存和工作内存构成&#xff0c;两个线程想要正常通信需要将工作内存中的变量刷到主存中&#xff0c;另一个线程才能正确读取得…

【数据结构】移除链表元素-图文解析(单链表OJ题)

LeetCode链接&#xff1a;203. 移除链表元素 - 力扣&#xff08;LeetCode&#xff09; 本文导航 &#x1f4ad;做题思路 &#x1f3a8;画图更好理解&#xff1a; ✍️代码实现 &#x1f5c2;️分情况讨论&#xff1a; ❄️极端情况&#xff1a; &#x1f4ad;做题思路 遍历链表…

Git报错合集

本文记录了笔者在使用 github 过程中遇到的问题&#xff0c;仅供个人使用。 目录 Could not resolve hostlocal changes to the following files would be overwritten by mergeTLS connection was non-properly terminatedUpdates were rejected because the remote contains …

普及100Hz高刷+1ms响应 微星发布27寸显示器:仅售799元

不论办公还是游戏&#xff0c;高刷及低响应时间都很重要&#xff0c;微星现在推出了一款27寸显示器PRO MP273A&#xff0c; 售价只有799元&#xff0c;但支持100Hz高刷、1ms响应时间&#xff0c;还有FreeSync技术减少撕裂。 PRO MP273A的100Hz高刷新率是其最大的卖点之一&#…

scala连接mysql数据库

scala中通常是通过JDBC组件来连接Mysql。JDBC, 全称为Java DataBase Connectivity standard。 加载依赖 其中包含 JDBC driver <dependency><groupId>mysql</groupId><artifactId>mysql-connector-java</artifactId><version>8.0.29&l…

eclipse Java Code_Style Code_Templates

Preferences - Java - Code Style - Code Templates Eclipse [Java_Code_Style_Code_Templates_ZengWenFeng] 2023.08.07.xml 创建一个新的工程&#xff0c;不然有时候不生效&#xff0c;旧项目可能要重新导入eclipse 创建一个测试类试一试 所有的设置都生效了

Java8实战-总结11

Java8实战-总结11 Lambda表达式方法引用管中窥豹如何构建方法引用 构造函数引用 Lambda表达式 方法引用 方法引用让你可以重复使用现有的方法定义&#xff0c;并像Lambda一样传递它们。在一些情况下&#xff0c;比起使用Lambda表达式&#xff0c;它们似乎更易读&#xff0c;感…

算法竞赛入门【码蹄集新手村600题】(MT1120-1140)C语言

算法竞赛入门【码蹄集新手村600题】(MT1120-1140&#xff09;C语言 目录MT1121 小码哥考完咯MT1122阶梯IF-ELSEMT1123 元音MT1124 罗马数字MT1125 几月份MT1126 十二生肖MT1127 小码哥的属相MT1128 骰子的反面MT1129 小码哥玩骰子MT1130 骰子里面的数学MT1131 字符判断MT1132 人…

SciencePub学术 | 算法类重点SCIEEI征稿中

SciencePub学术 (www.sciencepub.cn) 刊源推荐: 算法类重点SCIE&EI征稿中&#xff01;2区闭源好刊&#xff0c;对国人非常友好。信息如下&#xff0c;录满为止&#xff1a; 一、期刊概况&#xff1a; 算法类重点SCIE&EI 【期刊简介】IF&#xff1a;6.0-6.5&#xff0…

Acwing.876 快速幂求逆元

题目 给定n组ai ,pi&#xff0c;其中p;是质数,求α;模p;的乘法逆元&#xff0c;若逆元不存在则输出impossible。 输入格式 第一行包含整数n。 接下来n行&#xff0c;每行包含一个数组ai, pi&#xff0c;数据保证p;是质数。 输出格式 输出共n行&#xff0c;每组数据输出一…

钉钉对接打通金蝶云星空获取流程实例列表详情(宜搭)接口与其他应收单接口

钉钉对接打通金蝶云星空获取流程实例列表详情&#xff08;宜搭&#xff09;接口与其他应收单接口 对接系统钉钉 钉钉&#xff08;DingTalk&#xff09;是阿里巴巴集团专为中国企业打造的免费沟通和协同的多端平台&#xff0c;提供PC版&#xff0c;Web版和手机版&#xff0c;有考…

pytorch学习——卷积神经网络——以LeNet为例

目录 一.什么是卷积&#xff1f; 二.卷积神经网络的组成 三.卷积网络基本元素介绍 3.1卷积 3.2填充和步幅 3.2.1填充&#xff08;Padding&#xff09; 填充是指在输入数据周围添加额外的边界值&#xff08;通常是零&#xff09;&#xff0c;以扩展输入的尺寸。填充可以在卷…

Git工具安装

Git 工具安装 1. 下载Git安装包2. 安装Git工具3. 简单的使用配置用户名 1. 下载Git安装包 打开官网 https://git-scm.com/downloads点击下载 2. 安装Git工具 右击以管理员身份运行 ![在这里插入图片描述](https://img-blog.csdnimg.cn/9a99a73d54824800bc87db64f71f7602.png…

避免安装这5种软件,手机广告频繁弹窗且性能下降

在我们使用手机的日常生活中&#xff0c;选择合适的应用软件对于保持良好的使用体验至关重要。然而&#xff0c;有些软件可能会给我们带来不必要的麻烦和困扰。特别是那些频繁弹窗广告、导致手机性能下降的应用程序&#xff0c;我们应该尽量避免安装它们。 首先第一种&#xf…

Python-面向对象:面向对象、成员方法 、类和对象、构造方法、魔术方法、封装、继承、类型注解、多态(抽象类(接口))

版本说明 当前版本号[20230806]。 版本修改说明20230806初版 目录 文章目录 版本说明目录知识总览图面向对象初识对象生活中数据的组织程序中数据的组织使用对象组织数据 成员方法类的定义和使用成员变量和成员方法成员方法的定义语法注意事项 类和对象现实世界的事物和类使…