OpenHarmony开发者论坛
标题:
grpc-js三方库移植(二)——移植策略
[打印本页]
作者:
深开鸿_董伟
时间:
昨天 10:27
标题:
grpc-js三方库移植(二)——移植策略
[md]# grpc-js三方库移植(二)——移植策略
## 简介
新建ets项目,创建library库,并将grpc-js主要功能代码拷贝至library目录下,进行原生node.js的ts代码进行arkTs环境下的node适配,解决编译问题,在应用demo中调用library导出的方法,进行功能调试。
## 具体步骤
### 一、项目构建
#### 版本依赖
IDE版本 DevEco Studio 5.0.1 Release
下载路径:
[
https://developer.huawei.com/consumer/cn/download/
](
https://developer.huawei.com/consumer/cn/download/
)
#### 新建项目
新建应用,在应用中进行移植适配和功能调试
![createModule.png](
https://forums-obs.openharmony.c ... 3ew173u37epetpl.png
"createModule.png")
![](file://D:\2024%E5%B9%B4%E6%8A%80%E6%9C%AF%E6%96%87%E6%A1%A3%E8%BE%93%E5%87%BA\createModule.png?lastModify=1737426241)
#### 新建library
新建Static Library
![newLibrary.png](
https://forums-obs.openharmony.c ... 17qfjek1n4qlm8n.png
"newLibrary.png")
![](file://D:\2024%E5%B9%B4%E6%8A%80%E6%9C%AF%E6%96%87%E6%A1%A3%E8%BE%93%E5%87%BA\newLibrary.png?lastModify=1737426241)
#### 配置文件
在entry模块中引入依赖 library库
![entryJson.png](
https://forums-obs.openharmony.c ... dixtt95s7iduit5.png
"entryJson.png")
![](file://D:\2024%E5%B9%B4%E6%8A%80%E6%9C%AF%E6%96%87%E6%A1%A3%E8%BE%93%E5%87%BA\entryJson.png?lastModify=1737426241)
#### 代码移植
grpc-js源代码路径
![grpcJs.png](
https://forums-obs.openharmony.c ... 4j4qsssq17p5q13.png
"grpcJs.png")
![](file://D:\2024%E5%B9%B4%E6%8A%80%E6%9C%AF%E6%96%87%E6%A1%A3%E8%BE%93%E5%87%BA\grpcJs.png?lastModify=1737426241)
ohos应用中grpc-js代码存放路径(将上图中的src目录下所有文件拷贝至library模块新建的ts目录下)
![ohosGrpc.png](
https://forums-obs.openharmony.c ... 3u5sy3361464sz2.png
"ohosGrpc.png")
![](file://D:\2024%E5%B9%B4%E6%8A%80%E6%9C%AF%E6%96%87%E6%A1%A3%E8%BE%93%E5%87%BA\ohosGrpc.png?lastModify=1737426241)
### 二、基本使用
#### library库方法导出
library/Index.ets文件
```
import * as grpc from './src/main/ts'
export { grpc }
```
#### entry中ets后缀文件调用library库方法
```
import { grpc } from 'library'
```
#### entry中ts后缀文件调用library库方法
前置条件:将library/Index.ets 文件改为 library/Index.ts文件
grpc导入方法也与ets文件调用有所不同:
```
import { grpc } from "library/Index";
```
### 三、编译适配
由于grpc-js在node环境依赖的很多模块以及语法的检查上,和arkTs并不都一致,所以grpc-js内的ts代码放到library库下使用时,会出现一些语法以及代码功能上的错误,需要进行适配,总的思路就是,用arkTs的模块来代替node原生但在arkTs不支持的模块,首先是确保编译可以通过,然后再进行功能的调试。
#### 功能模块查找替换
##### 示例1(arkTs中存在同功能模块):
原代码:
```
export interface CaCertificateUpdate {
caCertificate: Buffer;
}
```
Buffer是node.js的原生类型,arkTs不存在Buffer类型,使用@ohos.buffer模块的buffer.Buffer类型替换
```
import buffer from '@ohos.buffer';
export type Buffer = buffer.Buffer;
```
##### 示例2(arkTs中不存在同功能模块,需要编写wrapper):
原代码
```
import { promises as dns } from 'dns';
private alternativeResolver = new dns.Resolver();
this.alternativeResolver.setServers([target.authority]);
this.alternativeResolver.resolve4(hostname),
this.alternativeResolver.resolve6(hostname),
this.alternativeResolver.resolveTxt(hostname);
const addressList = await dns.lookup(hostname, { all: true });
return dns.resolveTxt(hostname);
```
arkTs中不存在dns模块,无法使用类似的导入,这时候需要编写一个wrapper,实现一个dns的类,使其具备node.js中dns模块在grpc-js里面有用到的功能
编写dns wrapper:
```
// 创建WrapperResolver类,用于创建dns对象实例,constructor中打印log,后续代码调试时可查看调用信息
export class WrapperResolver {
private DOMAIN = 0x8691
private TAG = 'WrapperResolver'
private serverList: string[];
constructor() {
hilog.info(this.DOMAIN, this.TAG, 'create Resolver');
}
public getServers(): string[] {
return [
'8.8.8.8',
'2001:4860:4860::8888',
'8.8.8.8:1053',
'[2001:4860:4860::8888]:1053',
]
}
public setServers(paramList: string[]) {
this.serverList = paramList;
}
public resolve(){
}
public resolve4(param: string){
return param;
}
public resolve6(param: string){
return param;
}
public resolveAny(){}
public resolveCaa(){}
public resolveCname(){}
public resolveMx(){}
public resolveNaptr(){}
public resolveNs(){}
public resolvePtr(){}
public resolveSoa(){}
public resolveSrv(){}
public resolveTxt(param: string): Promise<string[][]>{
return [][param];
}
public reverse(){}
}
// dns实例
export class dns {
static lookup(hostname: string, arg1: { all: boolean }) {
let result
romise<LookupAddress[]>;
return result
}
static Resolver() {
return new WrapperResolver();
}
static resolveTxt(hostname: string): Promise<string[][]> {
return [][hostname];
}
}
```
替换dns wrapper原代码调用:
```
import { dns, WrapperResolver } from './wrapper/dns';
private alternativeResolver: WrapperResolver;
this.alternativeResolver = new WrapperResolver();
this.alternativeResolver.setServers([target.authority]);
this.alternativeResolver.resolve4(hostname),
this.alternativeResolver.resolve6(hostname),
this.alternativeResolver.resolveTxt(hostname);
const addressList = await dns.lookup(hostname, { all: true });
return dns.resolveTxt(hostname);
```
可以看出来,除了类是单独构建并替换了原有的导入,代码中的改动是非常小的,只在创建实例的地方因为调用方法不同有些许改动,这样编写wrapper,代码后续维护也非常方便,只需要改动wrapper即可。
由于植入的wrapper定义的部分接口并没有具体的实现,所以接口调用时必须打印一些有辨识度的log,否则调试功能,程序运行时可能不知道执行到哪一步了。
[/md]
欢迎光临 OpenHarmony开发者论坛 (https://forums.openharmony.cn/)
Powered by Discuz! X3.5