From 8b8d2fe7d268eb8d099da78aa8818c8b232e76e7 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:14:25 +0800 Subject: [PATCH 01/91] =?UTF-8?q?"modifile=20napi=5Fvs=5Fplugin/src/extens?= =?UTF-8?q?ion.js=20=E5=88=A0=E9=99=A4examples/napitutorials/tool/?= =?UTF-8?q?=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html=E4=B8=AD?= =?UTF-8?q?=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- napi_vs_plugin/src/extension.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/napi_vs_plugin/src/extension.js b/napi_vs_plugin/src/extension.js index 0f0d0b40..94602978 100644 --- a/napi_vs_plugin/src/extension.js +++ b/napi_vs_plugin/src/extension.js @@ -155,7 +155,7 @@ function register(context, command) { var result = { msg: "selectInterPath", path: tt ? uri.fsPath : "" - } + }; globalPanel.webview.postMessage(result); } }); -- Gitee From bda2bdec053892b3905db2e274eab819f86b2b47 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:15:52 +0800 Subject: [PATCH 02/91] =?UTF-8?q?"modifile=20napi=5Fvs=5Fplugin/src/gen/to?= =?UTF-8?q?ols/VsPluginLog.js=20=E5=88=A0=E9=99=A4examples/napitutorials/t?= =?UTF-8?q?ool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html?= =?UTF-8?q?=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- napi_vs_plugin/src/gen/tools/VsPluginLog.js | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/napi_vs_plugin/src/gen/tools/VsPluginLog.js b/napi_vs_plugin/src/gen/tools/VsPluginLog.js index 6ce4e7e3..254b3b5a 100644 --- a/napi_vs_plugin/src/gen/tools/VsPluginLog.js +++ b/napi_vs_plugin/src/gen/tools/VsPluginLog.js @@ -23,10 +23,10 @@ VsPluginLog.LEV_ERROR = 1; VsPluginLog.LEV_DEBUG = 2; VsPluginLog.LEV_INFO = 3; -const LEV_STR = ["[NON]", "[ERR]", "[DBG]", "[INF]"] +const LEV_STR = ["[NON]", "[ERR]", "[DBG]", "[INF]"]; var logLevel = VsPluginLog.LEV_ERROR; var logFileName = null; -var logResultMessage = [true, ""] +var logResultMessage = [true, ""]; function getDateString() { let nowDate = new Date(); @@ -44,7 +44,7 @@ VsPluginLog.init = function (level, fileName) { logLevel = level in [VsPluginLog.LEV_NONE, VsPluginLog.LEV_ERROR, VsPluginLog.LEV_DEBUG, VsPluginLog.LEV_INFO] ? level : VsPluginLog.LEV_ERROR; logFileName = fileName ? fileName : "napi_generator.log"; -} +}; function recordLog(lev, ...args) { let dataStr = getDateString(); @@ -59,20 +59,20 @@ function recordLog(lev, ...args) { VsPluginLog.logError = function (...args) { recordLog(VsPluginLog.LEV_ERROR, args); -} +}; VsPluginLog.logDebug = function (...args) { recordLog(VsPluginLog.LEV_DEBUG, args); -} +}; VsPluginLog.logInfo = function (...args) { recordLog(VsPluginLog.LEV_INFO, args); -} +}; VsPluginLog.getResult = function () { return logResultMessage; -} +}; module.exports = { VsPluginLog -} \ No newline at end of file +}; \ No newline at end of file -- Gitee From ecbbd9a5ea1aa69946c1f643a750faa197a6698e Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:17:12 +0800 Subject: [PATCH 03/91] =?UTF-8?q?"modifile=20napi=5Fvs=5Fplugin/src/gen/to?= =?UTF-8?q?ols/VsPluginRe.js=20=E5=88=A0=E9=99=A4examples/napitutorials/to?= =?UTF-8?q?ol/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html?= =?UTF-8?q?=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- napi_vs_plugin/src/gen/tools/VsPluginRe.js | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/napi_vs_plugin/src/gen/tools/VsPluginRe.js b/napi_vs_plugin/src/gen/tools/VsPluginRe.js index 909d7d54..bd22ad47 100644 --- a/napi_vs_plugin/src/gen/tools/VsPluginRe.js +++ b/napi_vs_plugin/src/gen/tools/VsPluginRe.js @@ -15,18 +15,18 @@ const path = require('path'); function search(ss, data) { - ss = replaceAll(ss, "\\.", "\\.") + ss = replaceAll(ss, "\\.", "\\."); let reg = new RegExp(ss); let tt = reg.exec(data); if (tt == null) return null; - let ret = { "regs": [] } + let ret = { "regs": [] }; for (let i = 0; i < tt.length; i++) { let p = data.indexOf(tt[i]); if (tt[i] == null) { - ret["regs"].push([-1, -1]) + ret["regs"].push([-1, -1]); } else { - ret["regs"].push([p, p + tt[i].length]) + ret["regs"].push([p, p + tt[i].length]); } } @@ -34,7 +34,7 @@ function search(ss, data) { } function match(ss, data) { - let tt = search(ss, data) + let tt = search(ss, data); if (tt != null && tt.regs[0][0] == 0) return tt; return null; } @@ -52,7 +52,7 @@ function all(sfrom) { } function replaceAll(ss, sfrom, sto) { - return ss.replace(all(sfrom), sto) + return ss.replace(all(sfrom), sto); } module.exports = { @@ -62,4 +62,4 @@ module.exports = { getPathInPath, replaceAll, all -} \ No newline at end of file +}; \ No newline at end of file -- Gitee From a47365ff0642bd9f4af6f4e0a2bfbee314ced6c5 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:18:21 +0800 Subject: [PATCH 04/91] =?UTF-8?q?"modifile=20napi=5Fvs=5Fplugin/src/vs=5Fc?= =?UTF-8?q?onfig=5Fview.html=20=E5=88=A0=E9=99=A4examples/napitutorials/to?= =?UTF-8?q?ol/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html?= =?UTF-8?q?=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- napi_vs_plugin/src/vs_config_view.html | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/napi_vs_plugin/src/vs_config_view.html b/napi_vs_plugin/src/vs_config_view.html index 6c35bb74..e5a7e673 100644 --- a/napi_vs_plugin/src/vs_config_view.html +++ b/napi_vs_plugin/src/vs_config_view.html @@ -138,7 +138,7 @@ var result = { msg: "selectIncludeName", mode: 2 - } + }; vscode.postMessage(result); } @@ -146,23 +146,23 @@ var result = { msg: "selectCppName", mode: 3 - } + }; vscode.postMessage(result); } function cancel() { var result = { msg: "cancelShowInfo" - } + }; vscode.postMessage(result); } function setIndex(index) { - clickIndex = index + clickIndex = index; } function getIndex() { - return clickIndex + return clickIndex; } window.addEventListener('message', event => { @@ -186,7 +186,7 @@ document.getElementById("serviceCode").value = event.data.updateInfo.updateServiceCode; } } - }) + }); -- Gitee From 9b7e2c24993ec3123ba02a87561dc98d779f2365 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:18:49 +0800 Subject: [PATCH 05/91] =?UTF-8?q?"modifile=20napi=5Fvs=5Fplugin/src/vs=5Fp?= =?UTF-8?q?lugin=5Fview.html=20=E5=88=A0=E9=99=A4examples/napitutorials/to?= =?UTF-8?q?ol/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html?= =?UTF-8?q?=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- napi_vs_plugin/src/vs_plugin_view.html | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/napi_vs_plugin/src/vs_plugin_view.html b/napi_vs_plugin/src/vs_plugin_view.html index 87e65775..71e79a9d 100644 --- a/napi_vs_plugin/src/vs_plugin_view.html +++ b/napi_vs_plugin/src/vs_plugin_view.html @@ -110,7 +110,7 @@ mode = 0; } }); - } + }; function sendParamMsg() { var fileNames = document.getElementById("interfaceFile").value; @@ -125,7 +125,7 @@ numberType: numberType, importIsCheck: importCheck, buttonName: buttonName, - } + }; vscode.postMessage(result); } @@ -133,21 +133,21 @@ var result = { msg: "selectInterPath", mode: mode - } + }; vscode.postMessage(result); } function selectPath(message) { var result = { msg: message - } + }; vscode.postMessage(result); } function cancel() { var result = { msg: "cancel" - } + }; vscode.postMessage(result); } @@ -160,7 +160,7 @@ genDir: genDir, mode: mode, interFile: document.getElementById("interfaceFile").value - } + }; vscode.postMessage(result); } @@ -182,7 +182,7 @@ } else { console.log("param is error"); } - }) + }); function inputChange() { var fileNames = document.getElementById("interfaceFile").value; -- Gitee From e1354392a0f753f7eb1293e174c3fb0f56755fe9 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:19:42 +0800 Subject: [PATCH 06/91] =?UTF-8?q?"modifile=20napi=5Fvs=5Fplugin/src/vs=5Fs?= =?UTF-8?q?howInfo=5Fview.html=20=E5=88=A0=E9=99=A4examples/napitutorials/?= =?UTF-8?q?tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html?= =?UTF-8?q?=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- napi_vs_plugin/src/vs_showInfo_view.html | 32 ++++++++++++------------ 1 file changed, 16 insertions(+), 16 deletions(-) diff --git a/napi_vs_plugin/src/vs_showInfo_view.html b/napi_vs_plugin/src/vs_showInfo_view.html index d7b25da7..7e08f05a 100644 --- a/napi_vs_plugin/src/vs_showInfo_view.html +++ b/napi_vs_plugin/src/vs_showInfo_view.html @@ -145,7 +145,7 @@ function cancel() { var result = { msg: "cancelShowInfo" - } + }; vscode.postMessage(result); } @@ -184,24 +184,24 @@ function renderList(configList, listElement) { configList.forEach((configItem, index) => { const listItem = document.createElement('tr'); - const itemContent1 = document.createElement('th') - itemContent1.textContent = configItem.includeName - const itemContent2 = document.createElement('th') - itemContent2.textContent = configItem.cppName - const itemContent3 = document.createElement('th') - itemContent3.textContent = configItem.interfaceName - const itemContent4 = document.createElement('th') - itemContent4.textContent = configItem.serviceCode - listItem.appendChild(itemContent1) - listItem.appendChild(itemContent2) - listItem.appendChild(itemContent3) - listItem.appendChild(itemContent4) + const itemContent1 = document.createElement('th'); + itemContent1.textContent = configItem.includeName; + const itemContent2 = document.createElement('th'); + itemContent2.textContent = configItem.cppName; + const itemContent3 = document.createElement('th'); + itemContent3.textContent = configItem.interfaceName; + const itemContent4 = document.createElement('th'); + itemContent4.textContent = configItem.serviceCode; + listItem.appendChild(itemContent1); + listItem.appendChild(itemContent2); + listItem.appendChild(itemContent3); + listItem.appendChild(itemContent4); listItem.addEventListener('click', () => { highlightItem(listElement, index); setIndex(index); setUpdateInfo(configItem.includeName, configItem.cppName, configItem.interfaceName, configItem.serviceCode); - }) + }); listElement.appendChild(listItem); }); } @@ -211,13 +211,13 @@ // 初始化 if (message.msg === 'initShowInfo') { const listElement = document.getElementById('configList'); - renderList(message.configList, listElement) + renderList(message.configList, listElement); } else if (message.msg === 'deleteData'){ const listElement = document.getElementById('configList'); while (listElement.firstChild) { listElement.removeChild(listElement.firstChild); } - renderList(message.configList, listElement) + renderList(message.configList, listElement); } }); -- Gitee From 1c00eb64278aecfcfea058db78692cccb4fed918 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:20:16 +0800 Subject: [PATCH 07/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/docs/guide/INSTRUCTION=5FZH.md=20=E5=88=A0=E9=99=A4e?= =?UTF-8?q?xamples/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../commandLine/docs/guide/INSTRUCTION_ZH.md | 819 ------------------ 1 file changed, 819 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/docs/guide/INSTRUCTION_ZH.md diff --git a/examples/napitutorials/tool/commandLine/docs/guide/INSTRUCTION_ZH.md b/examples/napitutorials/tool/commandLine/docs/guide/INSTRUCTION_ZH.md deleted file mode 100644 index 074d284f..00000000 --- a/examples/napitutorials/tool/commandLine/docs/guide/INSTRUCTION_ZH.md +++ /dev/null @@ -1,819 +0,0 @@ -# Native生成工具使用说明 - -## 准备 - -### 依赖 - -系统:建议Windows 10 - -开发工具:DevEco Studio - -## 生成框架 - -### 创建工程 - -1.打开 DevEco Studio: - -选择Create Project -> Application -> Native C++ ,然后点击Next,将Project name修改为cJsonSampleTest,点击Finish,则工程创建成功。 - -![image-20240508095733751](../../../figures/DevEco_create_new_project.png) - -![image-20240508095757468](../../../figures/DevEco_create_new_project_finish.png) - -### 导入三方库 - -将待转换的三方库导入工程中,如将cJSON三方库导入工程: - -1.cJSON三方库获取:[测试用三方库](https://gitee.com/openharmony/napi_generator/releases/tag/测试用资源) 选择cJSON.zip下载 - -![image-20240508100218813](../../../figures/download_thirdparty.png) - -2.将三方库导入工程:将cJSON.zip解压,解压后可以拷贝内容进 cJsonSampleTest\entry\src\main\cpp\thirdparty 和 cJsonSampleTest\entry\libs 下 - -![image-20240508100502230](../../../figures/DevEco_import_libs.png) - -同时将arm64-v8a/lib下的所有.so文件拷贝一份至arm64-v8a下,将armeabi-v7a/lib下的所有.so文件拷贝一份至armeabi-v7a下。 - -3.将libcjson加入编译:在CMakeLists.txt(cJsonSampleTest/entry/src/main/cpp/CMakeLists.txt)中加入libcjson路径 - -``` -set(CJSON_LIB_PATH ${NATIVERENDER_ROOT_PATH}/../../../libs/${OHOS_ARCH}) -``` - -在target_link_libraries中加入hilog和libcjson.so: - -``` -libhilog_ndk.z.so -``` - -``` -${CJSON_LIB_PATH}/libcjson.so -``` - -![image-20240508100005194](../../../figures/DevEco_add_thirdparty_lib.png) - -4.修改编译选项:在cJsonSampleTest/entry/build-profile.json5文件中buildOption中增加abiFilters字段, 并将targets字段的runtimeOS改为OpenHarmony - -``` -"abiFilters": [ - "arm64-v8a", - "armeabi-v7a" - ] -``` - -``` -"runtimeOS": "OpenHarmony" -``` - -![image-20240508100544906](../../../figures/DevEco_add_buildOption.png) - -### 使用nativetool生成框架 - -#### 准备 - -##### 1.在本地新建文件夹nativetoolGen - -##### **2.下载native_gen-win.exe**, header_parser.exe - -下载 [native_gen-win.exe](https://gitee.com/openharmony/napi_generator/releases/tag/测试用资源) 可执行程序和 [header_parser.exe](https://gitee.com/openharmony/napi_generator/releases/tag/测试用资源) 可执行程序,将其拷贝到nativetoolGen目录下 - -![image-20240508143053083](../../../figures/DevEco_Download_exe.png) - -#### 使用命令行生成框架 - -##### 1.运行可执行文件 - -1.1将待转换的.h文件放到nativetoolGen目录下,例如:将cJSON.h文件放入nativetoolGen目录下(cJSON.h可从导入的三方库下的include文件夹中获取) - -![image-20240508143053083](../../../figures/DevEco_add_hFile.png) - -1.2在命令行使用 以下命令运行脚本 - -``` -native_gen-win.exe -f 接口文件路径 -o 生成路径 -t 测试文件路径 -i 声明文件路径 -``` - -其中,参数详情如下: - --f, 必选参数,待转换的.h文件;如cJSON.h。 - --t, 可选参数,测试用例文件Ability.test.ets文件路径,默认路径为.h文件目录下testout文件夹下创建的xxxAbility.test.ets文件路径(如:testout/cJSONAbility.test.ets)。 - --i, 可选参数,ts声明文件index.s.ts文件路径,默认路径为.h文件目录下tsout文件夹下创建的index.d.ts文件路径(如:tsout/index.d.ts) - -index.d.ts文件路径; - --o, 可选参数,生成的.cpp文件所在路径,默认路径为.h文件目录下创建的cppout文件夹路径; - -例如: - -``` -native_gen-win.exe -f cJSON.h -``` - -1.3运行成功后命令行会打印出 Generate success; - -![image-20240508143053083](../../../figures/DevEco_generate_success.png) - -并在nativetoolGen/cppout目录下会生成方法的cpp文件: 分别是cjsonnapi.h(cJSON.h中接口对应的napi接口声明),cjsoninit.cpp(所有napi接口的init,用来初始化模块),cjsoncommon.h、cjsoncommon.cpp(公共方法的声明和实现,如获取错误信息方法)和cJSON.h中接口对应的cpp文件:每个cJSON.h中的接口对应一个cpp文件,该文件中为框架生成的cJSON接口的napi框架代码,如:cjsoncreateobject.cpp, cjsonparse.cpp 等等。在nativetoolGen/tsout/index.d.ts文件中会写入生成的ts接口;在nativetoolGen/testout/cJSONAbility.test.ets生成接口测试代码模板。 - -![image-20240508143053083](../../../figures/DevEco_generate_success_result.png) - -##### 2.确认生成代码是否能正确编译 - -2.1将cppout(nativetoolGen/cppout)拷贝至 cJsonSampleTest/entry/src/main/cpp目录下; 将cJSON.h拷贝至cppout目录下。 - -2.2将生成的所有cpp文件加入CMakeLists.txt(cJsonSampleTest/entry/src/main/cpp/CMakeLists.txt)编译,其中cppout/cjsoninit.cpp为编译入口;即用下列add_library替换原有的add_library - -``` -add_library(entry SHARED - cppout/cjsonparse.cpp - cppout/cjsoninithooks.cpp - cppout/cjsonaddarraytoobject.cpp - cppout/cjsonaddbooltoobject.cpp - cppout/cjsonaddfalsetoobject.cpp - cppout/cjsonadditemreferencetoarray.cpp - cppout/cjsonadditemreferencetoobject.cpp - cppout/cjsonadditemtoarray.cpp - cppout/cjsonadditemtoobject.cpp - cppout/cjsonadditemtoobjectcs.cpp - cppout/cjsonaddnulltoobject.cpp - cppout/cjsonaddnumbertoobject.cpp - cppout/cjsonaddobjecttoobject.cpp - cppout/cjsonaddrawtoobject.cpp - cppout/cjsonaddstringtoobject.cpp - cppout/cjsonaddtruetoobject.cpp - cppout/cjsoncompare.cpp - cppout/cjsoncreatearray.cpp - cppout/cjsoncreatearrayreference.cpp - cppout/cjsoncreatebool.cpp - cppout/cjsoncreatedoublearray.cpp - cppout/cjsoncreatefalse.cpp - cppout/cjsoncreatefloatarray.cpp - cppout/cjsoncreateintarray.cpp - cppout/cjsoncreatenull.cpp - cppout/cjsoncreatenumber.cpp - cppout/cjsoncreateobject.cpp - cppout/cjsoncreateobjectreference.cpp - cppout/cjsoncreateraw.cpp - cppout/cjsoncreatestringarray.cpp - cppout/cjsoncreatestringreference.cpp - cppout/cjsoncreatetrue.cpp - cppout/cjsondelete.cpp - cppout/cjsondeleteitemfromarray.cpp - cppout/cjsondeleteitemfromobject.cpp - cppout/cjsondeleteitemfromobjectcasesensitive.cpp - cppout/cjsondetachitemfromarray.cpp - cppout/cjsondetachitemfromobject.cpp - cppout/cjsondetachitemfromobjectcasesensitive.cpp - cppout/cjsondetachitemviapointer.cpp - cppout/cjsonduplicate.cpp - cppout/cjsonfree.cpp - cppout/cjsongetarrayitem.cpp - cppout/cjsongetarraysize.cpp - cppout/cjsongeterrorptr.cpp - cppout/cjsongetnumbervalue.cpp - cppout/cjsongetobjectitem.cpp - cppout/cjsongetobjectitemcasesensitive.cpp - cppout/cjsongetstringvalue.cpp - cppout/cjsonhasobjectitem.cpp - cppout/cjsoninsertiteminarray.cpp - cppout/cjsonisarray.cpp - cppout/cjsonisbool.cpp - cppout/cjsonisfalse.cpp - cppout/cjsonisinvalid.cpp - cppout/cjsonisnull.cpp - cppout/cjsonisnumber.cpp - cppout/cjsonisobject.cpp - cppout/cjsonisraw.cpp - cppout/cjsonisstring.cpp - cppout/cjsonistrue.cpp - cppout/cjsonmalloc.cpp - cppout/cjsonminify.cpp - cppout/cjsonparsewithlength.cpp - cppout/cjsonparsewithlengthopts.cpp - cppout/cjsonparsewithopts.cpp - cppout/cjsonprint.cpp - cppout/cjsonprintbuffered.cpp - cppout/cjsonprintpreallocated.cpp - cppout/cjsonprintunformatted.cpp - cppout/cjsonreplaceiteminarray.cpp - cppout/cjsonreplaceiteminobject.cpp - cppout/cjsonreplaceiteminobjectcasesensitive.cpp - cppout/cjsonreplaceitemviapointer.cpp - cppout/cjsonsetnumberhelper.cpp - cppout/cjsonsetvaluestring.cpp - cppout/cjsonversion.cpp - cppout/cjsoncreatestring.cpp - cppout/cjsoncommon.cpp - cppout/cjsoninit.cpp - ) -``` - -2.4将index.d.ts(nativetoolGen/tsout/index.d.ts)中所有内容拷贝至 cJsonSampleTest/entry/src/main/cpp/types/libentry/index.d.ts中; - -2.5将nativetoolGen/testout/cJSONAbilitytest.test.ets拷贝到cJsonSampleTest/entry/src/ohosTest/ets/test目录下; - -在cJsonSampleTest/entry/src/ohosTest/ets/test/List.test.ets中导入cJSONAbilitytest.test.ets - -``` -import abilityTest from './Ability.test'; -import cJSONabilityTest from './cJSONAbility.test'; - -export default function testsuite() { - abilityTest(); - cJSONabilityTest(); -} -``` - -![image-20240508110824799](../../../figures/DevEco_add_abilitytest.png) - -2.6对工程签名:File->Project Structure ->Project -> Signing Configs - -![image-20240508111334952](../../../figures/DevEco_Sign_configs.png) - -运行cJSONAbilitytest.test.ets中的测试集cJSONActsAbilityTest,用例成功运行,并打印出相关log。 - -![image-20240508111334952](../../../figures/DevEco_test_allcases_success.png) - -例如:方法KH418_cJSON_Parse打印出默认对象值(以cJSON_Parse接口为例:本例子生成的方法为KH418_cJSON_Parse,其中KH418中的数字为随机生成,用户使用时数字可能不是418, 而是其它三位随机数。) - -``` - I KH418_cJSON_Parse result: {"next":{},"prev":{},"child":{},"type":1,"valuestring":"valuestring","valueint":1,"valuedouble":1,"string":"string"} -``` - -![image-20240508111334952](../../../figures/DevEco_test_gen_is_success.png) - -## 增加业务代码并测试 - -### 增加业务代码 - -以cjson_parse接口为例 - -1.在cjsonparse.cpp(cJsonSampleTest\entry\src\main\cpp\cppout)代码中 - -``` -// Todo: add business logic. 在这前后代码为框架所生成 -``` - -处加入业务代码: - -1.1将字符串转换为cJSON对象,调用cJSON_Parse方法; - -``` - cJSON *json = cJSON_Parse(valueIn); - if (json == nullptr) { - return nullptr; - } - cJSON *jsonChild = nullptr; - if (json != nullptr) { - jsonChild = json->child; - } - cJSON *jsonNext = nullptr; - if (jsonChild != nullptr) { - jsonNext = jsonChild->next; - } - delete[] valueIn; -``` - -1.2将native层转换成功的json对象对应转换为js层的对象:向框架生成的cJSON_ParseOut空对象中一一塞入json对象数据并返回js层。 - -增加业务代码之后的cjsonparse.cpp如下所示:(注意:本示例的方法名字是KH418_cJSON_Parse,用户使用时需要将KH418_cJSON_Parse方法名修改为自身的KHxxx_cJSON_Parse方法名) - -``` -#include "cjsonnapi.h" - -napi_value getCjsonChildOut2(napi_env env, napi_value childOut, cJSON *jsonChild) { - napi_status status; - const napi_extended_error_info *extended_error_info; - const char *tag = "[KH418_cJSON_Parse]"; - napi_value childTypeOut; - status = napi_create_int32(env, jsonChild->type, &childTypeOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_int32 jsonChild->type", tag); - return nullptr; - } - status = napi_set_named_property(env, childOut, "type", childTypeOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_set_named_property jsonChild->type", tag); - return nullptr; - } - napi_value childValueintOut; - status = napi_create_int32(env, jsonChild->valueint, &childValueintOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_int32 jsonChild->valueint", tag); - return nullptr; - } - status = napi_set_named_property(env, childOut, "valueint", childValueintOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_set_named_property jsonChild->valueint", tag); - return nullptr; - } - napi_value childValuedoubleOut; - status = napi_create_double(env, jsonChild->valuedouble, &childValuedoubleOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_double jsonChild->valuedouble", tag); - return nullptr; - } - status = napi_set_named_property(env, childOut, "valuedouble", childValuedoubleOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_set_named_property jsonChild->valuedouble", tag); - return nullptr; - } - return childOut; -} - -napi_value getCjsonChildOut(napi_env env, napi_value childOut, cJSON *jsonChild) { - napi_status status; - const napi_extended_error_info *extended_error_info; - const char *tag = "[KH418_cJSON_Parse]"; - // 将数据塞入child - if (jsonChild != nullptr) { - napi_value childValuestringOut; - status = napi_create_string_utf8(env, jsonChild->valuestring == nullptr ? "" : jsonChild->valuestring, - NAPI_AUTO_LENGTH, &childValuestringOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_string_utf8 jsonChild->valuestring", tag); - return nullptr; - } - status = napi_set_named_property(env, childOut, "valuestring", childValuestringOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_set_named_property jsonChild->valuestring", tag); - return nullptr; - } - napi_value childStringOut; - status = napi_create_string_utf8(env, jsonChild->string == nullptr ? "" : jsonChild->string, NAPI_AUTO_LENGTH, - &childStringOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_string_utf8 jsonChild->string", tag); - return nullptr; - } - status = napi_set_named_property(env, childOut, "string", childStringOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_set_named_property jsonChild->string", tag); - return nullptr; - } - childOut = getCjsonChildOut2(env, childOut, jsonChild); - } - return childOut; -} - -napi_value getCjsonNextOut2(napi_env env, napi_value nextOut, cJSON *jsonNext) { - napi_status status; - const napi_extended_error_info *extended_error_info; - const char *tag = "[KH418_cJSON_Parse]"; - napi_value nextTypeOut; - status = napi_create_int32(env, jsonNext->type, &nextTypeOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_int32 jsonNext->type", tag); - return nullptr; - } - status = napi_set_named_property(env, nextOut, "type", nextTypeOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_set_named_property jsonNext->type", tag); - return nullptr; - } - napi_value nextValueintOut; - status = napi_create_int32(env, jsonNext->valueint, &nextValueintOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_int32 jsonNext->valueint", tag); - return nullptr; - } - status = napi_set_named_property(env, nextOut, "valueint", nextValueintOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_set_named_property jsonNext->valueint", tag); - return nullptr; - } - napi_value nextValuedoubleOut; - status = napi_create_double(env, jsonNext->valuedouble, &nextValuedoubleOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_double jsonNext->valuedouble", tag); - return nullptr; - } - status = napi_set_named_property(env, nextOut, "valuedouble", nextValuedoubleOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_set_named_property jsonNext->valuedouble", tag); - return nullptr; - } - return nextOut; -} - -napi_value getCjsonNextOut(napi_env env, napi_value nextOut, cJSON *jsonNext) { - napi_status status; - const napi_extended_error_info *extended_error_info; - const char *tag = "[KH418_cJSON_Parse]"; - // 将数据塞入next - if (jsonNext != nullptr) { - napi_value nextValuestringOut; - status = napi_create_string_utf8(env, jsonNext->valuestring == nullptr ? "" : jsonNext->valuestring, - NAPI_AUTO_LENGTH, &nextValuestringOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_string_utf8 jsonNext->valuestring", tag); - return nullptr; - } - status = napi_set_named_property(env, nextOut, "valuestring", nextValuestringOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_set_named_property jsonNext->valuestring", tag); - return nullptr; - } - napi_value nextStringOut; - status = napi_create_string_utf8(env, jsonNext->string == nullptr ? "" : jsonNext->string, NAPI_AUTO_LENGTH, - &nextStringOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_string_utf8 jsonNext->string", tag); - return nullptr; - } - status = napi_set_named_property(env, nextOut, "string", nextStringOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_set_named_property jsonNext->string", tag); - return nullptr; - } - nextOut = getCjsonNextOut2(env, nextOut, jsonNext); - } - return nextOut; -} - -napi_value getCjsonparseOut1(napi_env env, cJSON *jsonNext, napi_value cJSON_ParseOut) { - napi_status status; - const napi_extended_error_info *extended_error_info; - const char *tag = "[KH418_cJSON_Parse]"; - napi_value nextOut; - /* [NAPI_GEN]: 返回值是对象时,需要使用napi_create_object创建一个js的对象与js代码交互 - * env: 当前环境的句柄 - * result: 一个napi_value的指针,该指针将被设置为新创建的js对象 - */ - status = napi_create_object(env, &nextOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_object", tag); - return nullptr; - } - nextOut = getCjsonNextOut(env, nextOut, jsonNext); - /* [NAPI_GEN]: 返回值是对象时,将native侧的对象的属性和值依次塞入napi_create_object创建出的对象,后将该对象返回js - * env: 当前环境的句柄 - * object: 要设置属性的js对象,该对象是由上文napi_create_object创建的 - * utf8name: 属性的名称,是一个以UTF-8编码的字符串 - * value: 与属性名称关联的值,这个值可以是任何js类型(如一个数值、字符串、另一个对象等) - */ - status = napi_set_named_property(env, cJSON_ParseOut, "next", nextOut); - if (status != napi_ok) { - /* [NAPI_GEN]: 错误处理*/ - getErrMessage(status, env, extended_error_info, "napi_set_named_property", tag); - return nullptr; - } - napi_value prevOut; - /* [NAPI_GEN]: 返回值是对象时,需要使用napi_create_object创建一个js的对象与js代码交互 - * env: 当前环境的句柄 - * result: 一个napi_value的指针,该指针将被设置为新创建的js对象 - */ - status = napi_create_object(env, &prevOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_object", tag); - return nullptr; - } - /* [NAPI_GEN]: 返回值是对象时,将native侧的对象的属性和值依次塞入napi_create_object创建出的对象,将该对象返回js - * env: 当前环境的句柄 - * object: 要设置属性的js对象,该对象是由上文napi_create_object创建的 - * utf8name: 属性的名称,是一个以UTF-8编码的字符串 - * value: 与属性名称关联的值,这个值可以是任何js类型(如一个数值、字符串、另一个对象等) - */ - status = napi_set_named_property(env, cJSON_ParseOut, "prev", prevOut); - if (status != napi_ok) { - /* [NAPI_GEN]: 错误处理*/ - getErrMessage(status, env, extended_error_info, "napi_set_named_property", tag); - return nullptr; - } - return cJSON_ParseOut; -} - -napi_value getCjsonparseOut2(napi_env env, cJSON *json, cJSON *jsonChild, napi_value cJSON_ParseOut) { - napi_status status; - const napi_extended_error_info *extended_error_info; - const char *tag = "[KH418_cJSON_Parse]"; - napi_value childOut; - /* [NAPI_GEN]: 返回值是对象时,需要使用napi_create_object创建一个js的对象与js代码交互 - * env: 当前环境的句柄 - * result: 一个napi_value的指针,该指针将被设置为新创建的js对象 - */ - status = napi_create_object(env, &childOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_object", tag); - return nullptr; - } - childOut = getCjsonChildOut(env, childOut, jsonChild); - /* [NAPI_GEN]: - * 返回值是对象时,将native侧的对象的属性和值依次塞入napi_create_object创建出的对象,后将该对象返回js env: - * 当前环境的句柄 object: 要设置属性的js对象,该对象是由上文napi_create_object创建的 utf8name: - * 属性的名称,是一个以UTF-8编码的字符串 value: - * 与属性名称关联的值,这个值可以是任何js类型(如一个数值、字符串、另一个对象等) - */ - status = napi_set_named_property(env, cJSON_ParseOut, "child", childOut); - if (status != napi_ok) { - /* [NAPI_GEN]: 错误处理*/ - getErrMessage(status, env, extended_error_info, "napi_set_named_property", tag); - return nullptr; - } - napi_value typeOut; - /* [NAPI_GEN]: 返回值是int32_t类型时,napi_create_int32 创建一个包含32位整数(int32_t)的js数值(Number)对象 - * env: 当前环境的句柄 - * value: 要准换成js数值的int32_t的值,这里以传入1为例,用例新增业务代码时可根据自身需求修改 - * result: 指向napi_value的指针,这个指针会被设置为新创建的js数值对象 - */ - status = napi_create_int32(env, json == nullptr ? 0 : json->type, &typeOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_int32", tag); - return nullptr; - } - /* [NAPI_GEN]: 返回值是对象时,将native侧的对象的属性和值依次塞入napi_create_object创建出的对象,后将该对象返回js - * env: 当前环境的句柄 - * object: 要设置属性的js对象,该对象是由上文napi_create_object创建的 - * utf8name: 属性的名称,是一个以UTF-8编码的字符串 - * value: 与属性名称关联的值,这个值可以是任何js类型(如一个数值、字符串、另一个对象等) - */ - status = napi_set_named_property(env, cJSON_ParseOut, "type", typeOut); - if (status != napi_ok) { - /* [NAPI_GEN]: 错误处理*/ - getErrMessage(status, env, extended_error_info, "napi_set_named_property", tag); - return nullptr; - } - return cJSON_ParseOut; -} - -napi_value getCjsonparseOut3(napi_env env, cJSON *json, napi_value cJSON_ParseOut) { - napi_status status; - const napi_extended_error_info *extended_error_info; - const char *tag = "[KH418_cJSON_Parse]"; - napi_value valuestringOut; - /* [NAPI_GEN]: - * 返回值是字符串时,napi_create_string_utf8用于在原生代码中创建一个新的js字符串。这个函数会根据提供的UTF-8编码的字符串创建一个等价的js字符串 - * env: 当前环境的句柄 - * str: 指向以null结尾的UTF-8编码的C字符串的指针,这里以valuestring举例,用户可根据需求修改 - * length: - * 字符串的长度,可以是具体的字节数,或者使用特殊的值NAPI_AUTO_LENGTH来让函数自己计算长度(假定字符串以null结尾) - * result: 指向napi_value的指针,函数执行成功后这个指针将指向新创建的js字符串 - */ - status = - napi_create_string_utf8(env, json == nullptr ? "" : (json->valuestring == nullptr ? "" : json->valuestring), - NAPI_AUTO_LENGTH, &valuestringOut); - if (status != napi_ok) { - /*错误处理*/ - getErrMessage(status, env, extended_error_info, "napi_create_string_utf8", tag); - return nullptr; - } - /* [NAPI_GEN]: 返回值是对象时,将native侧的对象的属性和值依次塞入napi_create_object创建出的对象,后将该对象返回js - * env: 当前环境的句柄 - * object: 要设置属性的js对象,该对象是由上文napi_create_object创建的 - * utf8name: 属性的名称,是一个以UTF-8编码的字符串 - * value: 与属性名称关联的值,这个值可以是任何js类型(如一个数值、字符串、另一个对象等) - */ - status = napi_set_named_property(env, cJSON_ParseOut, "valuestring", valuestringOut); - if (status != napi_ok) { - /* [NAPI_GEN]: 错误处理*/ - getErrMessage(status, env, extended_error_info, "napi_set_named_property", tag); - return nullptr; - } - napi_value valueintOut; - /* [NAPI_GEN]: 返回值是int32_t类型时,napi_create_int32 创建一个包含32位整数(int32_t)的js数值(Number)对象 - * env: 当前环境的句柄 - * value: 要准换成js数值的int32_t的值,这里以传入1为例,用例新增业务代码时可根据自身需求修改 - * result: 指向napi_value的指针,这个指针会被设置为新创建的js数值对象 - */ - status = napi_create_int32(env, json == nullptr ? 0 : json->valueint, &valueintOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_int32", tag); - return nullptr; - } - /* [NAPI_GEN]: 返回值是对象时,将native侧的对象的属性和值依次塞入napi_create_object创建出的对象,后将该对象返回js - * env: 当前环境的句柄 - * object: 要设置属性的js对象,该对象是由上文napi_create_object创建的 - * utf8name: 属性的名称,是一个以UTF-8编码的字符串 - * value: 与属性名称关联的值,这个值可以是任何js类型(如一个数值、字符串、另一个对象等) - */ - status = napi_set_named_property(env, cJSON_ParseOut, "valueint", valueintOut); - if (status != napi_ok) { - /* [NAPI_GEN]: 错误处理*/ - getErrMessage(status, env, extended_error_info, "napi_set_named_property", tag); - return nullptr; - } - return cJSON_ParseOut; -} - -napi_value getCjsonparseOut4(napi_env env, cJSON *json, napi_value cJSON_ParseOut) { - napi_status status; - const napi_extended_error_info *extended_error_info; - const char *tag = "[KH418_cJSON_Parse]"; - napi_value valuedoubleOut; - /* [NAPI_GEN]: 返回值是double类型时,napi_create_double 创建一个包含双精度浮点数的js数值(Number)对象 - * env: 当前环境的句柄 - * value: 要传递给js的双精度浮点数值,这里以传入1.0为例,用例新增业务代码时可根据自身需求修改 - * result: 指向napi_value的指针,这个指针会被设置为新创建的js数值对象 - */ - status = napi_create_double(env, json == nullptr ? 0 : json->valuedouble, &valuedoubleOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_double", tag); - return nullptr; - } - /* [NAPI_GEN]: 返回值是对象时,将native侧的对象的属性和值依次塞入napi_create_object创建出的对象,后将该对象返回js - * env: 当前环境的句柄 - * object: 要设置属性的js对象,该对象是由上文napi_create_object创建的 - * utf8name: 属性的名称,是一个以UTF-8编码的字符串 - * value: 与属性名称关联的值,这个值可以是任何js类型(如一个数值、字符串、另一个对象等) - */ - status = napi_set_named_property(env, cJSON_ParseOut, "valuedouble", valuedoubleOut); - if (status != napi_ok) { - /* [NAPI_GEN]: 错误处理*/ - getErrMessage(status, env, extended_error_info, "napi_set_named_property", tag); - return nullptr; - } - napi_value stringOut; - /* [NAPI_GEN]: - * 返回值是字符串时,napi_create_string_utf8用于在原生代码中创建一个新的js字符串。这个函数会根据提供的UTF-8编码的字符串创建一个等价的js字符串 - * env: 当前环境的句柄 - * str: 指向以null结尾的UTF-8编码的C字符串的指针,这里以string举例,用户可根据需求修改 - * length: - * 字符串的长度,可以是具体的字节数,或者使用特殊的值NAPI_AUTO_LENGTH来让函数自己计算长度(假定字符串以null结尾) - * result: 指向napi_value的指针,函数执行成功后这个指针将指向新创建的js字符串 - */ - status = napi_create_string_utf8(env, json == nullptr ? "" : (json->string == nullptr ? "" : json->string), - NAPI_AUTO_LENGTH, &stringOut); - if (status != napi_ok) { - /*错误处理*/ - getErrMessage(status, env, extended_error_info, "napi_create_string_utf8", tag); - return nullptr; - } - /* [NAPI_GEN]: 返回值是对象时,将native侧的对象的属性和值依次塞入napi_create_object创建出的对象,后将该对象返回js - * env: 当前环境的句柄 - * object: 要设置属性的js对象,该对象是由上文napi_create_object创建的 - * utf8name: 属性的名称,是一个以UTF-8编码的字符串 - * value: 与属性名称关联的值,这个值可以是任何js类型(如一个数值、字符串、另一个对象等) - */ - status = napi_set_named_property(env, cJSON_ParseOut, "string", stringOut); - if (status != napi_ok) { - /* [NAPI_GEN]: 错误处理*/ - getErrMessage(status, env, extended_error_info, "napi_set_named_property", tag); - return nullptr; - } - return cJSON_ParseOut; -} - -/* [NAPI_GEN]:对应cJSON.h中:cJSON_Parse的napi方法, - * 输入:value: const char *; - * 输出:cJSON * - */ -napi_value KH418_cJSON_Parse(napi_env env, napi_callback_info info) -{ - OH_LOG_Print(LOG_APP, LOG_INFO, LOG_PRINT_DOMAIN, "KH418_cJSON_Parse", "KH418_cJSON_Parse begins"); - napi_status status; - /* [NAPI_GEN]: Node.js在其N-API中用来提供错误的扩展信息的结构体,结构体包含以下字段 - * error_message: 一个指向错误详细字符串的指针,提供了关于错误的文本描述 - * engin_reserved: 一个保留给Js引擎使用的指针 - * error_code: 错误码,指示了错误的种类,比如napi_pending_exception表示有一个JavaScript异常未被清理。 - * engine_error_code:一个引擎特定的错误码,为引擎实现保留,具体含义依赖于使用的JavaScript引擎。 - * error_message_len:错误消息字符串的长度。 - */ - const napi_extended_error_info *extended_error_info; - /* [NAPI_GEN]: tag: 日志打印标签*/ - const char *tag = "[KH418_cJSON_Parse]"; - /* [NAPI_GEN]: get function param in*/ - /* [NAPI_GEN]: argc:js传入的参数个数 */ - size_t argc = PARAMS1; - /* [NAPI_GEN]: args: 一个数组,保存js传入的参数 */ - napi_value args[PARAMS1] = {nullptr}; - /* [NAPI_GEN]: napi_get_cb_info用于获取JS调用该函数时所传递的参数、接收参数的个数以及'this'的值 - * env: 当前环境的句柄,代表当前的Node.js环境 - * info: 回调信息句柄,代表当前回调的上下文 - * argc: 指向size_t的指针,开始应包含可接受的max参数数量,函数返回时,它将包含实际传递的参数数量 - * args: 一个足够大的数组,用于接收传递给回调函数的所有js参数。数组的大小应至少与argc传入的值一样大。 - * this_arg: 如果不是NULL,则返回js回调中this的值 - * data: 如果不是NULL,则返回与回调函数关联的任何可选数据。通常用于传递在创建函数时指定的静态数据 - */ - status = napi_get_cb_info(env, info, &argc, args, nullptr, nullptr); - if(status != napi_ok) { - /* [NAPI_GEN]: 错误处理*/ - getErrMessage(status, env,extended_error_info, "napi_get_cb_info", tag); - return nullptr; - } - /* [NAPI_GEN]: 从args数组中获取入参 */ - OH_LOG_Print(LOG_APP, LOG_INFO, LOG_PRINT_DOMAIN, "KH418_cJSON_Parse", "KH418_cJSON_Parse get param info begins"); - napi_valuetype valuetypevalue; - /* [NAPI_GEN]: 获取入参类型,第PARAMS0个入参 - * env: N-API环境的句柄,表示当前的上下文 - * value: 要检查类型的js值 - * result: 是一个指针,指向napi_valuetype枚举的值,函数会将结果存储在这里 - */ - status = napi_typeof(env, args[PARAMS0], &valuetypevalue); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_typeof", tag); - return nullptr; - } - size_t strSizePARAMS0 = 0; - /* [NAPI_GEN]: napi_get_value_string_utf8用于将Js字符串转换为UTF-8编码的C字符串 - * env: N-API环境的句柄,表示当前的上下文 - * value: 要转换的JavaScript字符串 - * buf: 用于存储结果的字符数组的指针 - * bufsize: 缓冲区大小,以字节为单位 - * result: 转换后的字符串的字节长度(不包括空终止符)。若干buf是NULL,则返回所需的缓冲区大小(包括空终止符) - */ - /* [NAPI_GEN]: buf参数是NULL时,用于获取所需缓冲区大小*/ - status = napi_get_value_string_utf8(env, args[PARAMS0], NULL, 0, &strSizePARAMS0); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "get value string", tag); - return nullptr; - } - char *valueIn = new char[strSizePARAMS0 + 1]; - /* [NAPI_GEN]: 用于获取字符串*/ - status = napi_get_value_string_utf8(env, args[PARAMS0], valueIn, strSizePARAMS0 + 1, &strSizePARAMS0); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "get value string", tag); - delete[] valueIn; - return nullptr; - } - // delete[] valueIn; // remember to delete memory - - OH_LOG_Print(LOG_APP, LOG_INFO, LOG_PRINT_DOMAIN, "KH418_cJSON_Parse", "KH418_cJSON_Parse get param info ends"); - - OH_LOG_Print(LOG_APP, LOG_INFO, LOG_PRINT_DOMAIN, "KH418_cJSON_Parse", "KH418_cJSON_Parse get return info begins"); - // Todo: add business logic. 在这前后代码为框架所生成 - cJSON *json = cJSON_Parse(valueIn); - if (json == nullptr) { - return nullptr; - } - cJSON *jsonChild = nullptr; - if (json != nullptr) { - jsonChild = json->child; - } - cJSON *jsonNext = nullptr; - if (jsonChild != nullptr) { - jsonNext = jsonChild->next; - } - delete[] valueIn; - - /* [NAPI_GEN]: function return value*/ - napi_value cJSON_ParseOut; - /* [NAPI_GEN]: 返回值是对象时,需要使用napi_create_object创建一个js的对象与js代码交互 - * env: 当前环境的句柄 - * result: 一个napi_value的指针,该指针将被设置为新创建的js对象 - */ - status = napi_create_object(env, &cJSON_ParseOut); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_object", tag); - return nullptr; - } - cJSON_ParseOut = getCjsonparseOut1(env, jsonNext, cJSON_ParseOut); - cJSON_ParseOut = getCjsonparseOut2(env, json, jsonChild, cJSON_ParseOut); - cJSON_ParseOut = getCjsonparseOut3(env, json, cJSON_ParseOut); - cJSON_ParseOut = getCjsonparseOut4(env, json, cJSON_ParseOut); - - cJSON_Delete(json); - - OH_LOG_Print(LOG_APP, LOG_INFO, LOG_PRINT_DOMAIN, "KH418_cJSON_Parse", "KH418_cJSON_Parse get return info ends"); - OH_LOG_Print(LOG_APP, LOG_INFO, LOG_PRINT_DOMAIN, "KH418_cJSON_Parse", "KH418_cJSON_Parse ends"); - return cJSON_ParseOut; - -} - -``` - -### 测试调用 - -以cjson_parse接口为例 - -1.在cJsonSampleTest/entry/src/ohosTest/ets/test/CjsonTest/CjsonTest.test.ets测试集中修改KH418_cJSON_Parse方法的测试用例 - -![image-20240508111649030](../../../figures/DevEco_add_businessTest_case.png) - -``` - it('KH418_cJSON_Parse', 0, () => { - // Defines a test case. This API supports three parameters: test case name, filter parameter, and test case function. - hilog.info(0x0000, 'testTag', '%{public}s', 'it KH418_cJSON_Parse begin'); - // 测试字符串的转换 - let value = '"helloworld"' - let result: testNapi.cJSON = testNapi.KH418_cJSON_Parse(value); - // 测试数字的转换 - let value2 = '1.8' - let result2: testNapi.cJSON = testNapi.KH418_cJSON_Parse(value2); - // 测试数组的转换 - let value3 = '["a","b"]' - let result3: testNapi.cJSON = testNapi.KH418_cJSON_Parse(value3); - // 测试对象的转换 - let value4 = '{"name":"JohnDoe","age":18}' - let result4: testNapi.cJSON = testNapi.KH418_cJSON_Parse(value4); - - // 打印结果 - console.info("Test NAPI KH418_cJSON_Parse result1: ", JSON.stringify(result)) - console.info("Test NAPI KH418_cJSON_Parse result2: ", JSON.stringify(result2)) - console.info("Test NAPI KH418_cJSON_Parse result3: ", JSON.stringify(result3)) - console.info("Test NAPI KH418_cJSON_Parse result4: ", JSON.stringify(result4)) - }) -``` - -2.运行 KH418_cJSON_Parse, 打印结果如下: - -``` -I Test NAPI KH418_cJSON_Parse result1: {"next":{},"prev":{},"child":{},"type":16,"valuestring":"helloworld","valueint":0,"valuedouble":0,"string":""} -I Test NAPI KH418_cJSON_Parse result2: {"next":{},"prev":{},"child":{},"type":8,"valuestring":"","valueint":1,"valuedouble":1.8,"string":""} -I Test NAPI KH418_cJSON_Parse result3: {"next":{"valuestring":"b","string":"","type":16,"valueint":0,"valuedouble":0},"prev":{},"child":{"valuestring":"a","string":"","type":16,"valueint":0,"valuedouble":0},"type":32,"valuestring":"","valueint":0,"valuedouble":0,"string":""} -I Test NAPI KH418_cJSON_Parse result4: {"next":{"valuestring":"","string":"age","type":8,"valueint":18,"valuedouble":18},"prev":{},"child":{"valuestring":"JohnDoe","string":"name","type":16,"valueint":0,"valuedouble":0},"type":64,"valuestring":"","valueint":0,"valuedouble":0,"string":""} -``` - -![image-20240508111649030](../../../figures/DevEco_test_add_businesscode_success.png) - -- Gitee From 2c4adc44652c338ff6d90b3e4b027c968ea8b513 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:21:49 +0800 Subject: [PATCH 08/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/package.json=20=E5=88=A0=E9=99=A4examples/napitutori?= =?UTF-8?q?als/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html?= =?UTF-8?q?=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../tool/commandLine/package.json | 45 ------------------- 1 file changed, 45 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/package.json diff --git a/examples/napitutorials/tool/commandLine/package.json b/examples/napitutorials/tool/commandLine/package.json deleted file mode 100644 index fbe8e18a..00000000 --- a/examples/napitutorials/tool/commandLine/package.json +++ /dev/null @@ -1,45 +0,0 @@ -{ - "name": "native_gen", - "version": "1.0.0", - "description": "", - "main": "main.js", - "scripts": { - "test": "echo \"Error: no test specified\" && exit 1" - }, - "author": "", - "license": "ISC", - "dependencies": { - "stdio": "^2.1.3", - "typescript": "^5.4.3" - }, - "bin": "./src/main.js", - "pkg": { - "assets": [ - "./src/json/directFunction/dtsTempleteDetails/declareTemplete.gen", - "./src/json/directFunction/initTempleteDetails/cppInitTemplete.gen", - "./src/json/directFunction/initTempleteDetails/funcInitTemplete.gen", - "./src/json/directFunction/cppTempleteDetails/funcBody/funcBodyTemplete.gen", - "./src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/int32_t.gen", - "./src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/int64_t.gen", - "./src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/uint32_t.gen", - "./src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/double.gen", - "./src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/bool.gen", - "./src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/string.gen", - "./src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcGetParamTemplete.gen", - "./src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/paramGenTemplete.gen", - "./src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/int32_t.gen", - "./src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/int64_t.gen", - "./src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/uint32_t.gen", - "./src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/double.gen", - "./src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/bool.gen", - "./src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/string.gen", - "./src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/returnObj/object.gen", - "./src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/returnObj/funcReturnObjectToSet.gen", - "./src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnTemplete.gen", - "./src/json/directFunction/cppTempleteDetails/funcHDeclare/funcHDeclare.gen", - "./src/json/directFunction/cppTempleteDetails/funcHDeclare/funcHDeclareTemplete.gen", - "./src/json/directFunction/testTempleteDetails/abilityTestTemplete.gen", - "./src/json/directFunction/testTempleteDetails/abilityTestFirstGenTemplete.gen" - ] - } -} -- Gitee From 3f93477088bfba04bf3dee97bb732916f3d2f4c6 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:22:49 +0800 Subject: [PATCH 09/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcBody/?= =?UTF-8?q?funcBodyTemplete.gen=20=E5=88=A0=E9=99=A4examples/napitutorials?= =?UTF-8?q?/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html?= =?UTF-8?q?=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../funcBody/funcBodyTemplete.gen | 23 ------------------- 1 file changed, 23 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcBodyTemplete.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcBodyTemplete.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcBodyTemplete.gen deleted file mode 100644 index cbf8c83e..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcBodyTemplete.gen +++ /dev/null @@ -1,23 +0,0 @@ -/* [NAPI_GEN]:对应[file_introduce_replace]中:[func_introduce_replace]的napi方法, - * 输入:[input_introduce_replace] - * 输出:[output_introduce_replace] - */ -napi_value [funcName](napi_env env, napi_callback_info info) -{ - OH_LOG_Print(LOG_APP, LOG_INFO, LOG_PRINT_DOMAIN, "[funcName]", "[funcName] begins"); - napi_status status; - /* [NAPI_GEN]: Node.js在其N-API中用来提供错误的扩展信息的结构体,结构体包含以下字段 - * error_message: 一个指向错误详细字符串的指针,提供了关于错误的文本描述 - * engin_reserved: 一个保留给Js引擎使用的指针 - * error_code: 错误码,指示了错误的种类,比如napi_pending_exception表示有一个JavaScript异常未被清理。 - * engine_error_code:一个引擎特定的错误码,为引擎实现保留,具体含义依赖于使用的JavaScript引擎。 - * error_message_len:错误消息字符串的长度。 - */ - const napi_extended_error_info *extended_error_info; - /* [NAPI_GEN]: tag: 日志打印标签*/ - const char *tag = "[[get_error_msg_tag]]"; - /* [NAPI_GEN]: get function param in*/ -[func_getParam_replace] - OH_LOG_Print(LOG_APP, LOG_INFO, LOG_PRINT_DOMAIN, "[funcName]", "[funcName] get return info begins"); -[func_return_replace] -} -- Gitee From 1796079f98a7a458ceeb07b8bab152715c4d11aa Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:24:08 +0800 Subject: [PATCH 10/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcBody/?= =?UTF-8?q?funcParamIn/funcGetParamTemplete.gen=20=E5=88=A0=E9=99=A4exampl?= =?UTF-8?q?es/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../funcParamIn/funcGetParamTemplete.gen | 23 ------------------- 1 file changed, 23 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcGetParamTemplete.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcGetParamTemplete.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcGetParamTemplete.gen deleted file mode 100644 index 4dde3d7a..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcGetParamTemplete.gen +++ /dev/null @@ -1,23 +0,0 @@ - /* [NAPI_GEN]: argc:js传入的参数个数 */ - size_t argc = [param_length]; - /* [NAPI_GEN]: args: 一个数组,保存js传入的参数 */ - napi_value args[[param_length]] = {nullptr}; - /* [NAPI_GEN]: napi_get_cb_info用于获取JS调用该函数时所传递的参数、接收参数的个数以及'this'的值 - * env: 当前环境的句柄,代表当前的Node.js环境 - * info: 回调信息句柄,代表当前回调的上下文 - * argc: 指向size_t的指针,最初应包含可接受的最大参数数量,函数返回时,它将包含实际传递的参数数量 - * args: 一个足够大的数组,用于接收传递给回调函数的所有js参数。数组的大小应至少与argc传入的值一样大。 - * this_arg: 如果不是NULL,则返回js回调中this的值 - * data: 如果不是NULL,则返回与回调函数关联的任何可选数据。通常用于传递在创建函数时指定的静态数据 - */ - status = napi_get_cb_info(env, info, &argc, args, nullptr, nullptr); - if(status != napi_ok) { - /* [NAPI_GEN]: 错误处理*/ - getErrMessage(status, env,extended_error_info, "napi_get_cb_info", tag); - return nullptr; - } - /* [NAPI_GEN]: 从args数组中获取入参 */ - OH_LOG_Print(LOG_APP, LOG_INFO, LOG_PRINT_DOMAIN, "[funcName]", "[funcName] get param info begins"); -[getParam_replace] - OH_LOG_Print(LOG_APP, LOG_INFO, LOG_PRINT_DOMAIN, "[funcName]", "[funcName] get param info ends"); - \ No newline at end of file -- Gitee From 7332a45ab4da5ca332e21d0bea25ccabf051fbe1 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:24:48 +0800 Subject: [PATCH 11/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcBody/?= =?UTF-8?q?funcParamIn/funcParamType/bool.gen=20=E5=88=A0=E9=99=A4examples?= =?UTF-8?q?/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../funcBody/funcParamIn/funcParamType/bool.gen | 12 ------------ 1 file changed, 12 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/bool.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/bool.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/bool.gen deleted file mode 100644 index 60a0c807..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/bool.gen +++ /dev/null @@ -1,12 +0,0 @@ - bool [param_name_replace]In = 0; - /* [NAPI_GEN]: napi_get_value_bool将一个 napi_value 类型的 js 布尔值转换成一个 C 语言的 bool 类型的数值 - * env: N-API环境的句柄,表示当前的上下文 - * value:要转换的JavaScript值 - * result:指向 bool 类型的指针,在这里函数将存储转换后的布尔值 - */ - status = napi_get_value_bool(env, args[[param_index_replace]], &[param_name_replace]In); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_get_value_bool", tag); - return nullptr; - } - -- Gitee From eaecc52822aec7d2cad97d5e0921f9ec2605e903 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:26:03 +0800 Subject: [PATCH 12/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcBody/?= =?UTF-8?q?funcParamIn/funcParamType/double.gen=20=E5=88=A0=E9=99=A4exampl?= =?UTF-8?q?es/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../funcBody/funcParamIn/funcParamType/double.gen | 11 ----------- 1 file changed, 11 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/double.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/double.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/double.gen deleted file mode 100644 index 407ca748..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/double.gen +++ /dev/null @@ -1,11 +0,0 @@ - double [param_name_replace]In = 0; - /* [NAPI_GEN]: napi_get_value_double将一个 napi_value 类型的 js 数值转换成一个 C 语言的 double 类型的数值 - * env: N-API环境的句柄,表示当前的上下文 - * value:要转换的JavaScript值 - * result:指向 double 类型的指针,在这里函数将存储转换后的双精度浮点数 - */ - status = napi_get_value_double(env, args[[param_index_replace]], &[param_name_replace]In); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_get_value_double", tag); - return nullptr; - } -- Gitee From 799e43bd0238e43e8669a6fabe1a7887a1b726eb Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:26:36 +0800 Subject: [PATCH 13/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcBody/?= =?UTF-8?q?funcParamIn/funcParamType/int32=5Ft.gen=20=E5=88=A0=E9=99=A4exa?= =?UTF-8?q?mples/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../funcBody/funcParamIn/funcParamType/int32_t.gen | 12 ------------ 1 file changed, 12 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/int32_t.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/int32_t.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/int32_t.gen deleted file mode 100644 index 9db74901..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/int32_t.gen +++ /dev/null @@ -1,12 +0,0 @@ - int32_t [param_name_replace]In = 0; - /* [NAPI_GEN]: napi_get_value_int32将一个 napi_value 类型的 js 数值转换成一个 C 语言的 int32_t 类型的数值 - * env: N-API环境的句柄,表示当前的上下文 - * value:要转换的JavaScript值 - * result:指向 int32_t 类型的指针,在这里函数将存储转换后的整数值 - */ - status = napi_get_value_int32(env, args[[param_index_replace]], &[param_name_replace]In); - if (status != napi_ok) { - /* [NAPI_GEN]: 错误处理*/ - getErrMessage(status, env, extended_error_info, "napi_get_value_int32", tag); - return nullptr; - } \ No newline at end of file -- Gitee From 490c6270bc485410074f225e7515d301c5880622 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:28:07 +0800 Subject: [PATCH 14/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcBody/?= =?UTF-8?q?funcParamIn/funcParamType/int64=5Ft.gen=20=E5=88=A0=E9=99=A4exa?= =?UTF-8?q?mples/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../funcBody/funcParamIn/funcParamType/int64_t.gen | 11 ----------- 1 file changed, 11 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/int64_t.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/int64_t.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/int64_t.gen deleted file mode 100644 index e74da39d..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/int64_t.gen +++ /dev/null @@ -1,11 +0,0 @@ - int64_t [param_name_replace]In = 0; - /* [NAPI_GEN]: napi_get_value_int64将一个 napi_value 类型的 js 布尔值转换成一个 C 语言的 int64_t 类型的数值 - * env: N-API环境的句柄,表示当前的上下文 - * value:要转换的JavaScript值 - * result:指向 int64_t 类型的指针,在这里函数将存储转换后的整数值 - */ - status = napi_get_value_int64(env, args[[param_index_replace]], &[param_name_replace]In); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_get_value_int64", tag); - return nullptr; - } -- Gitee From 7dfd038021abdc826b87f68aaf973e593ae34b72 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:29:47 +0800 Subject: [PATCH 15/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcBody/?= =?UTF-8?q?funcParamIn/funcParamType/string.gen=20=E5=88=A0=E9=99=A4exampl?= =?UTF-8?q?es/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../funcParamIn/funcParamType/string.gen | 23 ------------------- 1 file changed, 23 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/string.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/string.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/string.gen deleted file mode 100644 index 432cdb93..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/string.gen +++ /dev/null @@ -1,23 +0,0 @@ - size_t strSize[param_index_replace] = 0; - /* [NAPI_GEN]: napi_get_value_string_utf8用于将Js字符串转换为UTF-8编码的C字符串 - * env: N-API环境的句柄,表示当前的上下文 - * value: 要转换的JavaScript字符串 - * buf: 用于存储结果的字符数组的指针 - * bufsize: 缓冲区大小,以字节为单位 - * result: 转换后的字符串的字节长度(不包括空终止符)。若干buf是NULL,则返回所需的缓冲区大小(包括空终止符) - */ - /* [NAPI_GEN]: buf参数是NULL时,用于获取所需缓冲区大小*/ - status = napi_get_value_string_utf8(env, args[[param_index_replace]], NULL, 0, &strSize[param_index_replace]); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "get value string", tag); - return nullptr; - } - char *[param_name_replace]In = new char[strSize[param_index_replace] + 1]; - /* [NAPI_GEN]: 用于获取字符串*/ - status = napi_get_value_string_utf8(env, args[[param_index_replace]], [param_name_replace]In, strSize[param_index_replace] + 1, &strSize[param_index_replace]); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "get value string", tag); - delete[] [param_name_replace]In; - return nullptr; - } - // delete[] [param_name_replace]In; // remember to delete memory -- Gitee From ea4cf3e44d6de4958750ba09d28be046c181c0ab Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:30:02 +0800 Subject: [PATCH 16/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcBody/?= =?UTF-8?q?funcParamIn/funcParamType/uint32=5Ft.gen=20=E5=88=A0=E9=99=A4ex?= =?UTF-8?q?amples/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../funcBody/funcParamIn/funcParamType/uint32_t.gen | 11 ----------- 1 file changed, 11 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/uint32_t.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/uint32_t.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/uint32_t.gen deleted file mode 100644 index c50842c0..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/uint32_t.gen +++ /dev/null @@ -1,11 +0,0 @@ - uint32_t [param_name_replace]In = 0; - /* [NAPI_GEN]: napi_get_value_uint32将一个napi_value类型的js布尔值转换成一个C语言的uint32_t类型的数值,第[param_index_replace]个入参 - * env: N-API环境的句柄,表示当前的上下文 - * value:要转换的JavaScript值 - * result:指向 uint32_t 类型的指针,在这里函数将存储转换后的无符号整数 - */ - status = napi_get_value_uint32(env, args[[param_index_replace]], &[param_name_replace]In); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_get_value_uint32", tag); - return nullptr; - } -- Gitee From e9c9d423308083ae541642eccc7c5f881320a756 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:31:04 +0800 Subject: [PATCH 17/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcBody/?= =?UTF-8?q?funcParamIn/paramGenTemplete.gen=20=E5=88=A0=E9=99=A4examples/n?= =?UTF-8?q?apitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AA?= =?UTF-8?q?js=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../funcBody/funcParamIn/paramGenTemplete.gen | 12 ------------ 1 file changed, 12 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/paramGenTemplete.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/paramGenTemplete.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/paramGenTemplete.gen deleted file mode 100644 index fcf11ee9..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcParamIn/paramGenTemplete.gen +++ /dev/null @@ -1,12 +0,0 @@ - napi_valuetype valuetype[param_name_replace]; - /* [NAPI_GEN]: 获取入参类型,第[param_index_replace]个入参 - * env: N-API环境的句柄,表示当前的上下文 - * value: 要检查类型的js值 - * result: 是一个指针,指向napi_valuetype枚举的值,函数会将结果存储在这里 - */ - status = napi_typeof(env, args[[param_index_replace]], &valuetype[param_name_replace]); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_typeof", tag); - return nullptr; - } -[getParam_replace] \ No newline at end of file -- Gitee From 22adfa253d973273bac3f1933f41a1fbd6003a76 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:31:26 +0800 Subject: [PATCH 18/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcBody/?= =?UTF-8?q?funcReturnOut/funcReturnTemplete.gen=20=E5=88=A0=E9=99=A4exampl?= =?UTF-8?q?es/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../funcBody/funcReturnOut/funcReturnTemplete.gen | 7 ------- 1 file changed, 7 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnTemplete.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnTemplete.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnTemplete.gen deleted file mode 100644 index 612c2704..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnTemplete.gen +++ /dev/null @@ -1,7 +0,0 @@ - // Todo: add business logic. 在这前后代码为框架所生成 - - /* [NAPI_GEN]: function return value*/ -[return_replace] - OH_LOG_Print(LOG_APP, LOG_INFO, LOG_PRINT_DOMAIN, "[funcName]", "[funcName] get return info ends"); - OH_LOG_Print(LOG_APP, LOG_INFO, LOG_PRINT_DOMAIN, "[funcName]", "[funcName] ends"); - return [return_name]Out; -- Gitee From 9a4c8d5a2a7a04a10b2613d58997b553387ae61f Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:31:52 +0800 Subject: [PATCH 19/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcBody/?= =?UTF-8?q?funcReturnOut/funcReturnType/bool.gen=20=E5=88=A0=E9=99=A4examp?= =?UTF-8?q?les/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../funcBody/funcReturnOut/funcReturnType/bool.gen | 11 ----------- 1 file changed, 11 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/bool.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/bool.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/bool.gen deleted file mode 100644 index ee7e002b..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/bool.gen +++ /dev/null @@ -1,11 +0,0 @@ - napi_value [return_name_replace]Out; - /* [NAPI_GEN]: 返回值是bool类型时,napi_get_boolean创建一个表示布尔值的js Boolean对象 - * env: 当前环境的句柄 - * value: 希望表示的布尔值(C中的true或者false),这里以传入true为例,用例新增业务代码时可根据自身需求修改 - * result: 函数返回一个napi_value,它是对应于js Boolean对象的C语言表示 - */ - status = napi_get_boolean(env, true, &[return_name_replace]Out); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_get_boolean", tag); - return nullptr; - } -- Gitee From 5b3dda3cd95726d0cbba03541ec82cc65755e3e4 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:32:35 +0800 Subject: [PATCH 20/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcBody/?= =?UTF-8?q?funcReturnOut/funcReturnType/double.gen=20=E5=88=A0=E9=99=A4exa?= =?UTF-8?q?mples/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../funcBody/funcReturnOut/funcReturnType/double.gen | 11 ----------- 1 file changed, 11 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/double.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/double.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/double.gen deleted file mode 100644 index 1684b927..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/double.gen +++ /dev/null @@ -1,11 +0,0 @@ - napi_value [return_name_replace]Out; - /* [NAPI_GEN]: 返回值是double类型时,napi_create_double 创建一个包含双精度浮点数的js数值(Number)对象 - * env: 当前环境的句柄 - * value: 要传递给js的双精度浮点数值,这里以传入1.0为例,用例新增业务代码时可根据自身需求修改 - * result: 指向napi_value的指针,这个指针会被设置为新创建的js数值对象 - */ - status = napi_create_double(env, 1.0, &[return_name_replace]Out); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_double", tag); - return nullptr; - } -- Gitee From cb624b4aaaebffebf0d0aa3cf8f35e8af7498bc1 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:33:14 +0800 Subject: [PATCH 21/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcBody/?= =?UTF-8?q?funcReturnOut/funcReturnType/int32=5Ft.gen=20=E5=88=A0=E9=99=A4?= =?UTF-8?q?examples/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0?= =?UTF-8?q?=E5=87=A0=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../funcBody/funcReturnOut/funcReturnType/int32_t.gen | 11 ----------- 1 file changed, 11 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/int32_t.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/int32_t.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/int32_t.gen deleted file mode 100644 index fcf6299e..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/int32_t.gen +++ /dev/null @@ -1,11 +0,0 @@ - napi_value [return_name_replace]Out; - /* [NAPI_GEN]: 返回值是int32_t类型时,napi_create_int32 创建一个包含32位整数(int32_t)的js数值(Number)对象 - * env: 当前环境的句柄 - * value: 要准换成js数值的int32_t的值,这里以传入1为例,用例新增业务代码时可根据自身需求修改 - * result: 指向napi_value的指针,这个指针会被设置为新创建的js数值对象 - */ - status = napi_create_int32(env, 1, &[return_name_replace]Out); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_int32", tag); - return nullptr; - } -- Gitee From 720f9e3f5cc762c603709d6a4639aa07cae505a4 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:33:55 +0800 Subject: [PATCH 22/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcBody/?= =?UTF-8?q?funcReturnOut/funcReturnType/int64=5Ft.gen=20=E5=88=A0=E9=99=A4?= =?UTF-8?q?examples/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0?= =?UTF-8?q?=E5=87=A0=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../funcBody/funcReturnOut/funcReturnType/int64_t.gen | 11 ----------- 1 file changed, 11 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/int64_t.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/int64_t.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/int64_t.gen deleted file mode 100644 index 8ff72bc6..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/int64_t.gen +++ /dev/null @@ -1,11 +0,0 @@ - napi_value [return_name_replace]Out; - /* [NAPI_GEN]: 返回值是int64类型时,napi_create_int64创建一个包含64位整数(int64_t)的js数值对象 - * env: 当前环境的句柄 - * value: 要转换成js数值的int64_t值,这里以传入1为例,用例新增业务代码时可根据自身需求修改 - * result: 指向napi_value的指针,函数执行成功后这个指针将指向新创建的js数值对象 - */ - status = napi_create_int64(env, 1, &[return_name_replace]Out); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_int64", tag); - return nullptr; - } -- Gitee From b2c6699b171c982fd4149e5f5099b9d88e561a03 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:33:59 +0800 Subject: [PATCH 23/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcBody/?= =?UTF-8?q?funcReturnOut/funcReturnType/returnObj/funcReturnObjectToSet.ge?= =?UTF-8?q?n=20=E5=88=A0=E9=99=A4examples/napitutorials/tool/=EF=BC=9B?= =?UTF-8?q?=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84?= =?UTF-8?q?;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../returnObj/funcReturnObjectToSet.gen | 12 ------------ 1 file changed, 12 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/returnObj/funcReturnObjectToSet.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/returnObj/funcReturnObjectToSet.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/returnObj/funcReturnObjectToSet.gen deleted file mode 100644 index 92a046e2..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/returnObj/funcReturnObjectToSet.gen +++ /dev/null @@ -1,12 +0,0 @@ - /* [NAPI_GEN]: 返回值是对象时,将native侧的对象的属性和值依次塞入napi_create_object创建出的对象,最终将该对象返回js - * env: 当前环境的句柄 - * object: 要设置属性的js对象,该对象是由上文napi_create_object创建的 - * utf8name: 属性的名称,是一个以UTF-8编码的字符串 - * value: 与属性名称关联的值,这个值可以是任何js类型(如一个数值、字符串、另一个对象等) - */ - status = napi_set_named_property(env, [set_objname_replace]Out, "[set_propname_replace]", [set_propvalue_replace]Out); - if (status != napi_ok) { - /* [NAPI_GEN]: 错误处理*/ - getErrMessage(status, env, extended_error_info, "napi_set_named_property", tag); - return nullptr; - } -- Gitee From eae6734887a49c20c3c3895d0f231dc5f4462e20 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:34:15 +0800 Subject: [PATCH 24/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcBody/?= =?UTF-8?q?funcReturnOut/funcReturnType/returnObj/object.gen=20=E5=88=A0?= =?UTF-8?q?=E9=99=A4examples/napitutorials/tool/=EF=BC=9B=E5=A2=9E?= =?UTF-8?q?=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../funcReturnOut/funcReturnType/returnObj/object.gen | 10 ---------- 1 file changed, 10 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/returnObj/object.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/returnObj/object.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/returnObj/object.gen deleted file mode 100644 index 2edd96c8..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/returnObj/object.gen +++ /dev/null @@ -1,10 +0,0 @@ - napi_value [return_name_replace]Out; - /* [NAPI_GEN]: 返回值是对象时,需要使用napi_create_object创建一个js的对象与js代码交互 - * env: 当前环境的句柄 - * result: 一个napi_value的指针,该指针将被设置为新创建的js对象 - */ - status = napi_create_object(env, &[return_name_replace]Out); - if (status != napi_ok) { - getErrMessage(status, env, extended_error_info, "napi_create_object", tag); - return nullptr; - } -- Gitee From 502d167195ac268cd1166b5ecda658451926ee9a Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:34:23 +0800 Subject: [PATCH 25/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcBody/?= =?UTF-8?q?funcReturnOut/funcReturnType/string.gen=20=E5=88=A0=E9=99=A4exa?= =?UTF-8?q?mples/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../funcReturnOut/funcReturnType/string.gen | 13 ------------- 1 file changed, 13 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/string.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/string.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/string.gen deleted file mode 100644 index 7e00cced..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/string.gen +++ /dev/null @@ -1,13 +0,0 @@ - napi_value [return_name_replace]Out; - /* [NAPI_GEN]: 返回值是字符串时,napi_create_string_utf8用于在原生代码中创建一个新的js字符串。这个函数会根据提供的UTF-8编码的字符串创建一个等价的js字符串 - * env: 当前环境的句柄 - * str: 指向以null结尾的UTF-8编码的C字符串的指针,这里以[return_name_replace]举例,用户可根据需求修改 - * length: 字符串的长度,可以是具体的字节数,或者使用特殊的值NAPI_AUTO_LENGTH来让函数自己计算长度(假定字符串以null结尾) - * result: 指向napi_value的指针,函数执行成功后这个指针将指向新创建的js字符串 - */ - status = napi_create_string_utf8(env, "[return_name_replace]", NAPI_AUTO_LENGTH, &[return_name_replace]Out); - if (status != napi_ok) { - /*错误处理*/ - getErrMessage(status, env, extended_error_info, "napi_create_string_utf8", tag); - return nullptr; - } -- Gitee From ffe0bd89e36739ee9d23fbfac3118ee58b229806 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:34:44 +0800 Subject: [PATCH 26/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcBody/?= =?UTF-8?q?funcReturnOut/funcReturnType/uint32=5Ft.gen=20=E5=88=A0?= =?UTF-8?q?=E9=99=A4examples/napitutorials/tool/=EF=BC=9B=E5=A2=9E?= =?UTF-8?q?=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../funcReturnOut/funcReturnType/uint32_t.gen | 12 ------------ 1 file changed, 12 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/uint32_t.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/uint32_t.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/uint32_t.gen deleted file mode 100644 index 8353c0c1..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/uint32_t.gen +++ /dev/null @@ -1,12 +0,0 @@ - napi_value [return_name_replace]Out; - /* [NAPI_GEN]: 返回值是uint32_t类型时,napi_create_uint32创建一个包含32位无符号整数(uint32_t)的js数值对象 - * env: 当前环境的句柄 - * value: 要转换成js数值的uint32_t值,这里以传入1为例,用例新增业务代码时可根据自身需求修改 - * result: 指向napi_value的指针,函数执行成功后这个指针将指向新创建的js数值对象 - */ - status = napi_create_uint32(env, 1, &[return_name_replace]Out); - if (status != napi_ok) { - /*错误处理*/ - getErrMessage(status, env, extended_error_info, "napi_create_uint32", tag); - return nullptr; - } -- Gitee From ac2e04c18adbf70779c3d61903da8b70f007c9e8 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:36:03 +0800 Subject: [PATCH 27/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcHDecl?= =?UTF-8?q?are/funcHDeclare.gen=20=E5=88=A0=E9=99=A4examples/napitutorials?= =?UTF-8?q?/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html?= =?UTF-8?q?=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../cppTempleteDetails/funcHDeclare/funcHDeclare.gen | 5 ----- 1 file changed, 5 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcHDeclare/funcHDeclare.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcHDeclare/funcHDeclare.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcHDeclare/funcHDeclare.gen deleted file mode 100644 index 3ddd9e01..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcHDeclare/funcHDeclare.gen +++ /dev/null @@ -1,5 +0,0 @@ -/* [NAPI_GEN]:对应[file_introduce_replace]中:[func_introduce_replace]的napi方法, - * 输入:[input_introduce_replace] - * 输出:[output_introduce_replace] - */ -napi_value [funcName](napi_env env, napi_callback_info info); -- Gitee From f1f1b6f3b1667dc1a2f930a82e66e43679690adb Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:36:37 +0800 Subject: [PATCH 28/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/cppTempleteDetails/funcHDecl?= =?UTF-8?q?are/funcHDeclareTemplete.gen=20=E5=88=A0=E9=99=A4examples/napit?= =?UTF-8?q?utorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs?= =?UTF-8?q?=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../funcHDeclare/funcHDeclareTemplete.gen | 9 --------- 1 file changed, 9 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcHDeclare/funcHDeclareTemplete.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcHDeclare/funcHDeclareTemplete.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcHDeclare/funcHDeclareTemplete.gen deleted file mode 100644 index 7e96611d..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/cppTempleteDetails/funcHDeclare/funcHDeclareTemplete.gen +++ /dev/null @@ -1,9 +0,0 @@ - -#ifndef NAPITUTORIALS_[h_file_name_replace]_H -#define NAPITUTORIALS_[h_file_name_replace]_H - -#include "[h_filename_replace]common.h" - -[func_declare_replace] - -#endif //NAPITUTORIALS_[h_file_name_replace]_H \ No newline at end of file -- Gitee From 18f86cc1716b69311ae0c115edac9cd5b221d7b8 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:38:15 +0800 Subject: [PATCH 29/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/dtsTempleteDetails/declareTe?= =?UTF-8?q?mplete.gen=20=E5=88=A0=E9=99=A4examples/napitutorials/tool/?= =?UTF-8?q?=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html=E4=B8=AD?= =?UTF-8?q?=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../directFunction/dtsTempleteDetails/declareTemplete.gen | 5 ----- 1 file changed, 5 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/dtsTempleteDetails/declareTemplete.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/dtsTempleteDetails/declareTemplete.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/dtsTempleteDetails/declareTemplete.gen deleted file mode 100644 index 64fce4b1..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/dtsTempleteDetails/declareTemplete.gen +++ /dev/null @@ -1,5 +0,0 @@ -/* [NAPI_GEN]:对应[file_introduce_replace]中:[func_introduce_replace]方法的dts接口 - * 输入: [input_introduce_replace] - * 输出: [output_introduce_replace] - */ -[tab_replace][export_replace][func_name_replace]:([func_param_replace]) => [func_return_replace]; -- Gitee From 06b4996f85074cc05211330923a39e3f399a9f3d Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:39:37 +0800 Subject: [PATCH 30/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/initTempleteDetails/cppInitT?= =?UTF-8?q?emplete.gen=20=E5=88=A0=E9=99=A4examples/napitutorials/tool/?= =?UTF-8?q?=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html=E4=B8=AD?= =?UTF-8?q?=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../initTempleteDetails/cppInitTemplete.gen | 51 ------------------- 1 file changed, 51 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/initTempleteDetails/cppInitTemplete.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/initTempleteDetails/cppInitTemplete.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/initTempleteDetails/cppInitTemplete.gen deleted file mode 100644 index e278368f..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/initTempleteDetails/cppInitTemplete.gen +++ /dev/null @@ -1,51 +0,0 @@ -#include "napi/native_api.h" -#include -#include -[include_replace] - -EXTERN_C_START - -/*[NAPI_GEN]:Init函数被定义用来初始化模块(比如设置导出的函数或对象)*/ -static napi_value Init(napi_env env, napi_value exports) -{ - /* [NAPI_GEN]:napi_property_descriptor是Node.js中N-API的一个结构体,它用来描述一个对象的属性,这包括数据属性和访问器 - * 属性(通常是getter和setter函数), 这个结构体包含了以下字段 - * utf8name: 属性的名称,以 null 结尾的 UTF-8 字符串。 - * name: 可选,代替 utf8name 的 napi_value 类型的名称。这允许使用预先存在的 napi_value,可能是一个字符串或符号。 - * method: 如果这个属性是一个函数,这里会是一个指向原生函数的指针。 - * getter: 如果这个属性有一个 getter 函数,这里会是一个指向该 getter 原生函数的指针。 - * setter: 如果这个属性有一个 setter 函数,这里会是一个指向该 setter 原生函数的指针。 - * value: 如果这个属性是一个数据属性,这里会是一个 napi_value 表示属性的值。 - * attributes: 属性的描述符,指定属性是否可写(napi_writable)、可枚举(napi_enumerable)、可配置(napi_configurable)等。 - * data: 一个指针,指向与属性相关联的任何原生数据。这通常用于存储与 getter 和 setter 相关联的上下文信息。 - */ - napi_property_descriptor desc[] = { -[init_replace] - }; - - /* [NAPI_GEN]:napi_define_properties 是一个N-API函数,它允许原生模块在 JavaScript 对象上定义新的属性。允许一次性定义多个属性。 - * 这个函数是在原生代码中定义对象形状的关键工具,可以用来向对象添加属性,包括数据属性和访问器属性(getter/setter) - * env: N-API 环境句柄,代表当前的运行环境。 - * object: 一个 napi_value,指向你想要定义属性的对象。 - * property_count: 属性描述符数组中的元素数量,告知函数有多少个属性需要定义。 - * properties: 指向 napi_property_descriptor 结构体数组的指针,每个结构体描述了一个要定义的属性。 - */ - napi_define_properties(env, exports, sizeof(desc) / sizeof(desc[0]), desc); - return exports; -} -EXTERN_C_END -static napi_module demoModule = { - .nm_version = 1, - .nm_flags = 0, - .nm_filename = nullptr, - .nm_register_func = Init, /*[NAPI_GEN]:将初始化函数Init与模块关联起来*/ - .nm_modname = "entry", - .nm_priv = ((void*)0), - .reserved = { 0 }, -}; - -extern "C" __attribute__((constructor)) void RegisterEntryModule(void) -{ - /*[NAPI_GEN]:napi_module_register 宏被用来静态注册模块初始化函数,使得Node.js在加载模块时调用它。*/ - napi_module_register(&demoModule); -} \ No newline at end of file -- Gitee From 4460bc2c2a4e467aeb4060870cd54f478122223c Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:40:49 +0800 Subject: [PATCH 31/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/initTempleteDetails/funcInit?= =?UTF-8?q?Templete.gen=20=E5=88=A0=E9=99=A4examples/napitutorials/tool/?= =?UTF-8?q?=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html=E4=B8=AD?= =?UTF-8?q?=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../directFunction/initTempleteDetails/funcInitTemplete.gen | 2 -- 1 file changed, 2 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/initTempleteDetails/funcInitTemplete.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/initTempleteDetails/funcInitTemplete.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/initTempleteDetails/funcInitTemplete.gen deleted file mode 100644 index ff9347e6..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/initTempleteDetails/funcInitTemplete.gen +++ /dev/null @@ -1,2 +0,0 @@ - // [NAPI_GEN]:方法注册后,js方法与native方法映射 - { "[func_name_replace]" , nullptr, [func_name_replace], nullptr, nullptr, nullptr, napi_default, nullptr }, -- Gitee From aaca9be5cc1dd071a6cd271bdedfecea37a84314 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:41:56 +0800 Subject: [PATCH 32/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/testTempleteDetails/abilityT?= =?UTF-8?q?estFirstGenTemplete.gen=20=E5=88=A0=E9=99=A4examples/napitutori?= =?UTF-8?q?als/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html?= =?UTF-8?q?=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../abilityTestFirstGenTemplete.gen | 28 ------------------- 1 file changed, 28 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/testTempleteDetails/abilityTestFirstGenTemplete.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/testTempleteDetails/abilityTestFirstGenTemplete.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/testTempleteDetails/abilityTestFirstGenTemplete.gen deleted file mode 100644 index 813ebacb..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/testTempleteDetails/abilityTestFirstGenTemplete.gen +++ /dev/null @@ -1,28 +0,0 @@ -import hilog from '@ohos.hilog'; -import testNapi from 'libentry.so'; -import { describe, beforeAll, beforeEach, afterEach, afterAll, it, expect } from '@ohos/hypium'; - -export default function [abilitytest_name_replace]abilityTest() { - describe('[abilitytest_name_replace]ActsAbilityTest', () => { - // Defines a test suite. Two parameters are supported: test suite name and test suite function. - beforeAll(() => { - // Presets an action, which is performed only once before all test cases of the test suite start. - // This API supports only one parameter: preset action function. - }) - beforeEach(() => { - // Presets an action, which is performed before each unit test case starts. - // The number of execution times is the same as the number of test cases defined by **it**. - // This API supports only one parameter: preset action function. - }) - afterEach(() => { - // Presets a clear action, which is performed after each unit test case ends. - // The number of execution times is the same as the number of test cases defined by **it**. - // This API supports only one parameter: clear action function. - }) - afterAll(() => { - // Presets a clear action, which is performed after all test cases of the test suite end. - // This API supports only one parameter: clear action function. - }) - - }) -} \ No newline at end of file -- Gitee From 4e2c2100ad20e8d6a8cce0f6a31883de85c5ebe2 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:42:52 +0800 Subject: [PATCH 33/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/directFunction/testTempleteDetails/abilityT?= =?UTF-8?q?estTemplete.gen=20=E5=88=A0=E9=99=A4examples/napitutorials/tool?= =?UTF-8?q?/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html?= =?UTF-8?q?=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../testTempleteDetails/abilityTestTemplete.gen | 13 ------------- 1 file changed, 13 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/directFunction/testTempleteDetails/abilityTestTemplete.gen diff --git a/examples/napitutorials/tool/commandLine/src/json/directFunction/testTempleteDetails/abilityTestTemplete.gen b/examples/napitutorials/tool/commandLine/src/json/directFunction/testTempleteDetails/abilityTestTemplete.gen deleted file mode 100644 index 2b7c86b2..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/directFunction/testTempleteDetails/abilityTestTemplete.gen +++ /dev/null @@ -1,13 +0,0 @@ -/* [NAPI_GEN]:对应[file_introduce_replace]中:[func_introduce_replace]方法的dts接口测试用例 - * 方法输入: [input_introduce_replace] - * 方法输出: [output_introduce_replace] - */ -it('[test_case_name]', 0, () => { - // Defines a test case. This API supports three parameters: test case name, filter parameter, and test case function. - hilog.info(0x0000, 'testTag', '%{public}s', 'it [test_case_name] begin'); - - [func_direct_testCase] - - // Defines a variety of assertion methods, which are used to declare expected boolean conditions. - // e.g. expect(result).assertEqual(2+3) -}) -- Gitee From d4c24f246f2e31bf10830d372efd9a26c2e94400 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:43:34 +0800 Subject: [PATCH 34/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/json/function.json=20=E5=88=A0=E9=99=A4examples/?= =?UTF-8?q?napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../tool/commandLine/src/json/function.json | 49 ------------------- 1 file changed, 49 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/json/function.json diff --git a/examples/napitutorials/tool/commandLine/src/json/function.json b/examples/napitutorials/tool/commandLine/src/json/function.json deleted file mode 100644 index 618c549c..00000000 --- a/examples/napitutorials/tool/commandLine/src/json/function.json +++ /dev/null @@ -1,49 +0,0 @@ -{ - "directFunction": { - "dtsTemplete": "../json/directFunction/dtsTempleteDetails/declareTemplete.gen", - "initTempleteDetails":{ - "cppInitTemplete": "../json/directFunction/initTempleteDetails/cppInitTemplete.gen", - "funcInitTemplete": "../json/directFunction/initTempleteDetails/funcInitTemplete.gen" - }, - "cppTempleteDetails": { - "funcBody":{ - "funcBodyTemplete": "../json/directFunction/cppTempleteDetails/funcBody/funcBodyTemplete.gen", - "funcParamIn":{ - "funcParamType": { - "int32_t": "../json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/int32_t.gen", - "int64_t": "../json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/int64_t.gen", - "uint32_t": "../json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/uint32_t.gen", - "double": "../json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/double.gen", - "bool": "../json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/bool.gen", - "string": "../json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcParamType/string.gen" - }, - "funcGetParamTemplete":"../json/directFunction/cppTempleteDetails/funcBody/funcParamIn/funcGetParamTemplete.gen", - "paramGenTemplete":"../json/directFunction/cppTempleteDetails/funcBody/funcParamIn/paramGenTemplete.gen" - }, - "funcReturnOut":{ - "funcReturnType": { - "int32_t": "../json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/int32_t.gen", - "int64_t": "../json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/int64_t.gen", - "uint32_t": "../json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/uint32_t.gen", - "double": "../json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/double.gen", - "bool": "../json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/bool.gen", - "string": "../json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/string.gen", - "returnObj":{ - "object": "../json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/returnObj/object.gen", - "funcReturnObjectToSet": "../json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnType/returnObj/funcReturnObjectToSet.gen" - } - }, - "funcReturnTemplete" : "../json/directFunction/cppTempleteDetails/funcBody/funcReturnOut/funcReturnTemplete.gen" - } - }, - "funcHDeclare": { - "funcHDeclare": "../json/directFunction/cppTempleteDetails/funcHDeclare/funcHDeclare.gen", - "funcHDeclareTemplete": "../json/directFunction/cppTempleteDetails/funcHDeclare/funcHDeclareTemplete.gen" - } - }, - "testTempleteDetails": { - "abilityTestTemplete": "../json/directFunction/testTempleteDetails/abilityTestTemplete.gen", - "abilityTestFirstGenTemplete": "../json/directFunction/testTempleteDetails/abilityTestFirstGenTemplete.gen" - } - } -} \ No newline at end of file -- Gitee From 5c80bede5d365f6ace1e4ab8e9f1fc22ffa70e89 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:45:04 +0800 Subject: [PATCH 35/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/main.js=20=E5=88=A0=E9=99=A4examples/napitutoria?= =?UTF-8?q?ls/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html?= =?UTF-8?q?=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../tool/commandLine/src/main.js | 62 ------------------- 1 file changed, 62 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/main.js diff --git a/examples/napitutorials/tool/commandLine/src/main.js b/examples/napitutorials/tool/commandLine/src/main.js deleted file mode 100644 index 59eaede2..00000000 --- a/examples/napitutorials/tool/commandLine/src/main.js +++ /dev/null @@ -1,62 +0,0 @@ -/* -* Copyright (c) 2024 Shenzhen Kaihong Digital Industry Development Co., Ltd. -* Licensed under the Apache License, Version 2.0 (the "License"); -* you may not use this file except in compliance with the License. -* You may obtain a copy of the License at -* -* http://www.apache.org/licenses/LICENSE-2.0 -* -* Unless required by applicable law or agreed to in writing, software -* distributed under the License is distributed on an "AS IS" BASIS, -* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -* See the License for the specific language governing permissions and -* limitations under the License. -*/ -const fs = require('fs'); -const path = require('path') -const stdio = require("stdio"); -const main = require("./TsGen/tsMain"); - -let ops = stdio.getopt({ - // 输入的.h文件路径,必填 - 'filename': { key: 'f', args: 1, description: ".h file", default: "" }, - // 可选参数,测试文件路径 - 'testFilename': { key: 't', args: 1, description: "Ability.test.ets file", default: "" }, - // 可选参数, 声明文件路径 - 'indexFilename': { key: 'i', args: 1, description: "index.d.ts file", default: "" }, - // 可选参数, cpp文件路径 - 'outCppPath': { key: 'o', args: 1, description: ".cpp dir path", default: "" }, -}); - -// 获取命令行参数 .h文件路径 -let filePath = ops.filename -let testFilePath = ops.testFilename -let tsFilePath = ops.indexFilename -let cppFilePath = ops.outCppPath -// 读取文件内容 判断参数是否为空 -if (filePath !== '') { - // 若用户没有提供路径 则程序提供默认路径 - if (!tsFilePath) { - createDirectorySync(path.join(filePath, '../tsout')) - tsFilePath = path.join(filePath, '../tsout/index.d.ts'); - } - if (!testFilePath) { - testFilePath = path.join(filePath, '../testout'); - createDirectorySync(testFilePath) - } - if(!cppFilePath) { - // 若用户未给定cpp生成路径,则在.h路径下直接生成out路径 - cppFilePath = path.join(filePath, '../cppout'); - createDirectorySync(cppFilePath) - } - - main.doGenerate(filePath, testFilePath, tsFilePath, cppFilePath); -} - -function createDirectorySync(directoryPath) { - try { - fs.mkdirSync(directoryPath, { recursive: true }); - } catch (err) { - console.error(`无法创建文件夹 ${directoryPath}: ${err}`); - } -} \ No newline at end of file -- Gitee From 68ec72a4055778b9b1d266403fbcb858a2b68162 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:45:10 +0800 Subject: [PATCH 36/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/napiGen/functionDirect.js=20=E5=88=A0=E9=99=A4ex?= =?UTF-8?q?amples/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../commandLine/src/napiGen/functionDirect.js | 304 ------------------ 1 file changed, 304 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/napiGen/functionDirect.js diff --git a/examples/napitutorials/tool/commandLine/src/napiGen/functionDirect.js b/examples/napitutorials/tool/commandLine/src/napiGen/functionDirect.js deleted file mode 100644 index 960ca0b1..00000000 --- a/examples/napitutorials/tool/commandLine/src/napiGen/functionDirect.js +++ /dev/null @@ -1,304 +0,0 @@ -/* -* Copyright (c) 2024 Shenzhen Kaihong Digital Industry Development Co., Ltd. -* Licensed under the Apache License, Version 2.0 (the "License"); -* you may not use this file except in compliance with the License. -* You may obtain a copy of the License at -* -* http://www.apache.org/licenses/LICENSE-2.0 -* -* Unless required by applicable law or agreed to in writing, software -* distributed under the License is distributed on an "AS IS" BASIS, -* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -* See the License for the specific language governing permissions and -* limitations under the License. -*/ - -const { NapiLog } = require("../tools/NapiLog"); -const util = require('util'); -const path = require('path'); -const fs = require("fs"); -const { writeFile, readFile } = require("../tools/tool"); -const re = require("../tools/re"); -const LENGTH = 10; -const TWO_DECIMAL = 2; - -function analyzeRetIsObject(retType, objectInfo) { - // 去除 * 和 空格 - retType = retType.replace('*', '').replace('struct', '').trim() - let objKeys = Object.keys(objectInfo) - for (let i = 0; i < objKeys.length; i++) { - if (retType == objKeys[i]) { - return true; - } - } - return false; -} - - -function analyzeRetIsTypeDef(type, info) { - let typedefKeys = Object.keys(info) - for (let i = 0; i < typedefKeys.length; i++) { - if (type === typedefKeys[i]) { - return info[type]; - } - } - return null; -} - -//tsFuncName -function generateDirectFunction(params, index, tsFuncName, directFuncPath, hFileName) { - let funcInfo = { - "name": "", - "params": [], - "retType": "", - } - - let funcName_replace = tsFuncName - - // 方法的注册 - let funcInitPath = path.join(__dirname, directFuncPath.initTempleteDetails.funcInitTemplete); - let funcInitTemplete = readFile(funcInitPath) - let init_replace = replaceAll(funcInitTemplete, '[func_name_replace]', funcName_replace) - - // 分析方法 分析第index个方法 - funcInfo.name = params.functions[index].name - funcInfo.retType = params.functions[index].rtnType - let parseParams = params.functions[index].parameters - for (let i = 0; i < parseParams.length; ++i) { - let param = createParam(parseParams[i]) - funcInfo.params.push(param) - } - - // 生成 - let relativeParamGenPath = directFuncPath.cppTempleteDetails.funcBody.funcParamIn.paramGenTemplete - let paramGenTempletePath = path.join(__dirname, relativeParamGenPath); - let paramGenTemplete = readFile(paramGenTempletePath) - let funcParamTypePath = directFuncPath.cppTempleteDetails.funcBody.funcParamIn.funcParamType - let paramGenResult = '' - // napi 获取参数 - for (let i = 0; i < funcInfo.params.length; i++) { - paramGenResult = getParamJs2C(funcInfo, i, paramGenTemplete, funcParamTypePath, paramGenResult, params); - } - - // 返回值处理 对于对象要使用循环处理 - let retGenResult = '' - let retObjInfo = { - "objName": '', - "flag": false - } - - let funcRetOutPath = directFuncPath.cppTempleteDetails.funcBody.funcReturnOut - retGenResult = returnTypeC2Js(funcRetOutPath, funcInfo, params, retGenResult, retObjInfo); - - let funcBodyTempletePath = path.join(__dirname, directFuncPath.cppTempleteDetails.funcBody.funcBodyTemplete); - let bodyTemplete = readFile(funcBodyTempletePath); - - let body_replace = replaceAll(bodyTemplete, '[funcName]', funcName_replace) - body_replace = replaceAll(body_replace, '[get_error_msg_tag]', funcName_replace) - body_replace = replaceAll(body_replace, '[file_introduce_replace]', hFileName) - body_replace = replaceAll(body_replace, '[func_introduce_replace]', funcInfo.name) - - let funcInfoParams = '' - let funcInfoParamTemp = '[paramName]: [paramType]; ' - for (let i = 0; i < funcInfo.params.length; i++) { - let funcInfoParamReplace = replaceAll(funcInfoParamTemp, '[paramName]', funcInfo.params[i].name) - funcInfoParamReplace = replaceAll(funcInfoParamReplace, '[paramType]', funcInfo.params[i].type) - funcInfoParams += funcInfoParamReplace - } - body_replace = replaceAll(body_replace, '[input_introduce_replace]', funcInfoParams === ''? 'void': funcInfoParams) - body_replace = replaceAll(body_replace, '[output_introduce_replace]', funcInfo.retType) - - let funcGetParamTempletePath = path.join(__dirname, - directFuncPath.cppTempleteDetails.funcBody.funcParamIn.funcGetParamTemplete); - let funcGetParamTemplete = readFile(funcGetParamTempletePath) - let genParam_replace = replaceAll(funcGetParamTemplete, '[param_length]', "PARAMS" + funcInfo.params.length) - genParam_replace = replaceAll(genParam_replace, '[funcName]', funcName_replace) - genParam_replace = replaceAll(genParam_replace, '[getParam_replace]', paramGenResult) - if (funcInfo.params.length !== 0) { - body_replace = replaceAll(body_replace, '[func_getParam_replace]', genParam_replace) - } else { - body_replace = replaceAll(body_replace, '[func_getParam_replace]', '') - } - if (funcInfo.retType.replace('*', '').trim() !== 'void') { - let returnType = funcInfo.retType === 'std::string' ? 'const char *' : funcInfo.retType - returnType = returnType === 'size_t' ? 'int64_t' : returnType - let funcReturnTempletePath = path.join(__dirname, funcRetOutPath.funcReturnTemplete); - let funcReturnTemplete = readFile(funcReturnTempletePath); - let = func_return_replace = replaceAll(funcReturnTemplete, '[return_name]', retObjInfo.objName) - func_return_replace = replaceAll(func_return_replace, '[funcName]', funcName_replace) - func_return_replace = replaceAll(func_return_replace, '[return_replace]', retGenResult) - body_replace = replaceAll(body_replace, '[func_return_replace]', func_return_replace) - } else { - body_replace = replaceAll(body_replace, '[func_return_replace]', ' return NULL;\n') - } - body_replace = replaceAll(body_replace, '[return_replace]', retGenResult) - - let funcHDeclarePath = path.join(__dirname, directFuncPath.cppTempleteDetails.funcHDeclare.funcHDeclare); - let funcHDeclare = readFile(funcHDeclarePath) - funcHDeclare = replaceAll(funcHDeclare, '[funcName]', funcName_replace) - - funcHDeclare = replaceAll(funcHDeclare, '[file_introduce_replace]', hFileName) - funcHDeclare = replaceAll(funcHDeclare, '[func_introduce_replace]', funcInfo.name) - funcHDeclare = replaceAll(funcHDeclare, '[input_introduce_replace]', funcInfoParams === ''? 'void': funcInfoParams) - funcHDeclare = replaceAll(funcHDeclare, '[output_introduce_replace]', funcInfo.retType) - - return [funcHDeclare, init_replace, body_replace] -} - -function getParamJs2C(funcInfo, i, paramGenTemplete, funcParamTypePath, paramGenResult, params) { - let paramType = funcInfo.params[i].type === 'size_t' ? 'int64_t' : funcInfo.params[i].type; - // 去除const 和 * - paramType = paramType.replace('const', '').replace('*', '').trim() - let paramName = funcInfo.params[i].name; - let paramGen = replaceAll(paramGenTemplete, '[param_index_replace]', "PARAMS" + i); - paramGen = replaceAll(paramGen, '[param_name_replace]', paramName); - if (paramType === 'double') { - let getParamPath = path.join(__dirname, funcParamTypePath.double) - paramGen = getParamGenCon(getParamPath, i, paramName, paramGen); - paramGenResult += paramGen; - } else if (paramType === 'uint32_t') { - let getParamPath = path.join(__dirname, funcParamTypePath.uint32_t) - paramGen = getParamGenCon(getParamPath, i, paramName, paramGen); - - paramGenResult += paramGen; - } else if (paramType === 'int32_t' || paramType === 'int') { - let getParamPath = path.join(__dirname, funcParamTypePath.int32_t) - paramGen = getParamGenCon(getParamPath, i, paramName, paramGen); - paramGenResult += paramGen; - } else if (paramType === 'int64_t' || paramType === 'size_t') { - let getParamPath = path.join(__dirname, funcParamTypePath.int64_t) - paramGen = getParamGenCon(getParamPath, i, paramName, paramGen); - paramGenResult += paramGen; - } else if (paramType === 'bool') { - let getParamPath = path.join(__dirname, funcParamTypePath.bool) - paramGen = getParamGenCon(getParamPath, i, paramName, paramGen); - paramGenResult += paramGen; - } else if (paramType === 'std::string' || paramType.indexOf('char') >= 0) { - let getParamPath = path.join(__dirname, funcParamTypePath.string) - paramGen = getParamGenCon(getParamPath, i, paramName, paramGen); - paramGenResult += paramGen; - } else if (analyzeRetIsTypeDef(paramType, params.typedefs)) { // typedefs - funcInfo.params[i].type = analyzeRetIsTypeDef(paramType, params.typedefs); - paramGenResult = getParamJs2C(funcInfo, i, paramGenTemplete, funcParamTypePath, paramGenResult, params); - } - // 其他情况,处理成对象 napi_get_cb_info之后不做任何处理 - return paramGenResult; -} - -function getParamGenCon(getParamPath, i, paramName, paramGen) { - let getParam = readFile(getParamPath); - getParam = replaceAll(getParam, '[param_index_replace]', "PARAMS" + i); - getParam = replaceAll(getParam, '[param_name_replace]', paramName); - paramGen = replaceAll(paramGen, '[getParam_replace]', getParam); - return paramGen; -} - -function returnTypeC2Js(funcRetOutPath, funcInfo, params, retGenResult, retObjInfo) { - let setRetPropertyPath = path.join(__dirname, funcRetOutPath.funcReturnType.returnObj.funcReturnObjectToSet) - let setRetProperty = readFile(setRetPropertyPath) - let returnName = funcInfo.name; - if (!retObjInfo.flag) { - retObjInfo.objName = returnName - } - if (funcInfo.retType === 'uint32_t') { - let funcReturnTypePath = path.join(__dirname, funcRetOutPath.funcReturnType.uint32_t) - retGenResult = getRetTypeContent(funcReturnTypePath, returnName, retGenResult, retObjInfo, setRetProperty); - } else if (funcInfo.retType === 'double') { - let funcReturnTypePath = path.join(__dirname, funcRetOutPath.funcReturnType.double) - retGenResult = getRetTypeContent(funcReturnTypePath, returnName, retGenResult, retObjInfo, setRetProperty); - } else if (funcInfo.retType === 'int32_t' || funcInfo.retType === 'int') { - let funcReturnTypePath = path.join(__dirname, funcRetOutPath.funcReturnType.int32_t) - retGenResult = getRetTypeContent(funcReturnTypePath, returnName, retGenResult, retObjInfo, setRetProperty); - } else if (funcInfo.retType === 'int64_t' || funcInfo.retType === 'size_t') { - let funcReturnTypePath = path.join(__dirname, funcRetOutPath.funcReturnType.int64_t) - retGenResult = getRetTypeContent(funcReturnTypePath, returnName, retGenResult, retObjInfo, setRetProperty); - } else if (funcInfo.retType === 'bool') { - let funcReturnTypePath = path.join(__dirname, funcRetOutPath.funcReturnType.bool) - retGenResult = getRetTypeContent(funcReturnTypePath, returnName, retGenResult, retObjInfo, setRetProperty); - } else if (funcInfo.retType === 'std::string' || funcInfo.retType.substring(0, 10) === 'const char' - || funcInfo.retType === 'char *') { - let funcReturnTypePath = path.join(__dirname, funcRetOutPath.funcReturnType.string) - retGenResult = getRetTypeContent(funcReturnTypePath, returnName, retGenResult, retObjInfo, setRetProperty); - } else if (analyzeRetIsObject(funcInfo.retType, params.classes)) { // 返回值是对象 - if (!retObjInfo.flag) { - retGenResult = getObjRetContent(funcRetOutPath, retGenResult, returnName); - retObjInfo.flag = true - let retType = funcInfo.retType.replace('*', '').trim(); - let objectName = ''; - let objectProperty = []; - - let myObject = params.classes[retType] - objectName = myObject.bare_name; - let myObjectProperty = myObject.properties.public; - for (let j = 0; j < myObjectProperty.length; j++) { - let propertyObj = { - "name": '', - "retType": '' - } - propertyObj.name = myObjectProperty[j].name; - propertyObj.retType = myObjectProperty[j].type; - - objectProperty.push(propertyObj); - } - // 遍历属性 - for (let i = 0; i < objectProperty.length; i++) { - let testRes = returnTypeC2Js(funcRetOutPath, objectProperty[i], params, retGenResult, retObjInfo) - retGenResult = testRes; - } - } else { - if (retObjInfo.objName !== '') { - retGenResult = getObjRetContent(funcRetOutPath, retGenResult, returnName); - let setRetPropertyObj = readFile(setRetPropertyPath) - setRetPropertyObj = replaceAll(setRetPropertyObj, '[set_objname_replace]', retObjInfo.objName); - setRetPropertyObj = replaceAll(setRetPropertyObj, '[set_propname_replace]', returnName); - setRetPropertyObj = replaceAll(setRetPropertyObj, '[set_propvalue_replace]', returnName); - retGenResult += setRetPropertyObj; - } - } - } else if (analyzeRetIsTypeDef(funcInfo.retType, params.typedefs)) { // typedefs - funcInfo.retType = analyzeRetIsTypeDef(funcInfo.retType, params.typedefs); - retGenResult = returnTypeC2Js(funcRetOutPath, funcInfo, params, retGenResult, retObjInfo); - } - return retGenResult; -} - -function getObjRetContent(funcRetOutPath, retGenResult, returnName) { - let funcReturnTypePath = path.join(__dirname, funcRetOutPath.funcReturnType.returnObj.object) - let funcReturnType = readFile(funcReturnTypePath); - retGenResult += replaceAll(funcReturnType, '[return_name_replace]', returnName); - return retGenResult; -} - -function getRetTypeContent(funcReturnTypePath, returnName, retGenResult, retObjInfo, setRetProperty) { - let funcReturnType = readFile(funcReturnTypePath); - funcReturnType = replaceAll(funcReturnType, '[return_name_replace]', returnName); - retGenResult += funcReturnType; - if (retObjInfo.flag) { - setRetProperty = replaceAll(setRetProperty, '[set_objname_replace]', retObjInfo.objName); - setRetProperty = replaceAll(setRetProperty, '[set_propname_replace]', returnName); - setRetProperty = replaceAll(setRetProperty, '[set_propvalue_replace]', returnName); - retGenResult += setRetProperty; - } - return retGenResult; -} - -function replaceAll(s, sfrom, sto) { - while (s.indexOf(sfrom) >= 0) { - s = s.replace(sfrom, sto) - } - return s; -} - -function createParam(parseParamInfo) { - let param = { - "name": "", - "type": "" - } - param.name = parseParamInfo.name - param.type = parseParamInfo.type - return param -} - -module.exports = { - generateDirectFunction -} \ No newline at end of file -- Gitee From c5480030b9ce3020c87ec1b091bd7c11d65cab77 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:45:21 +0800 Subject: [PATCH 37/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/napiGen/functionDirectTest.js=20=E5=88=A0?= =?UTF-8?q?=E9=99=A4examples/napitutorials/tool/=EF=BC=9B=E5=A2=9E?= =?UTF-8?q?=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../src/napiGen/functionDirectTest.js | 237 ------------------ 1 file changed, 237 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/napiGen/functionDirectTest.js diff --git a/examples/napitutorials/tool/commandLine/src/napiGen/functionDirectTest.js b/examples/napitutorials/tool/commandLine/src/napiGen/functionDirectTest.js deleted file mode 100644 index 78b51293..00000000 --- a/examples/napitutorials/tool/commandLine/src/napiGen/functionDirectTest.js +++ /dev/null @@ -1,237 +0,0 @@ -/* -* Copyright (c) 2024 Shenzhen Kaihong Digital Industry Development Co., Ltd. -* Licensed under the Apache License, Version 2.0 (the "License"); -* you may not use this file except in compliance with the License. -* You may obtain a copy of the License at -* -* http://www.apache.org/licenses/LICENSE-2.0 -* -* Unless required by applicable law or agreed to in writing, software -* distributed under the License is distributed on an "AS IS" BASIS, -* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -* See the License for the specific language governing permissions and -* limitations under the License. -*/ -const { NapiLog } = require("../tools/NapiLog"); -const util = require('util'); -const { generateRandomInteger } = require("../tools/tool"); -const { InterfaceList, TypeList } = require('../tools/common') -const path = require('path') -const fs = require("fs"); -const LENGTH = 10; -const TWO_DECIMAL = 2; -const MODTWO = 2; - -// 随机生成浮点数值 -function generateRandomArbitrary(min, max, fixed) { - let random = (Math.random() * (max - min) + min).toFixed(fixed); - return parseFloat(random); -} - -// 随机生成布尔值 -function generateRandomBoolValue() { - let randomBool = false; - if (generateRandomInteger(0, LENGTH) % MODTWO === 0) { - randomBool = true; - } - return randomBool; -} - -// 随机生成字符串 -function generateRandomString(length) { - let result = ''; - let characters = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789'; - let charactersLength = characters.length; - - for (let i = 0; i < length; i++) { - result += characters.charAt(Math.floor(Math.random() * charactersLength)); - } - - return result; -} - -function generateFuncTestCase(params, funcIndex, tsFuncName, abilityTestTemplete, hFileName) { - let funcInfo = { - "name": "", - "params": [], - "retType": "", - } - funcInfo.name = params.functions[funcIndex].name - let parseParams = params.functions[funcIndex].parameters - for(let i = 0; i < parseParams.length; ++i) { - let param = createParam(parseParams[i]) - funcInfo.params.push(param) - } - funcInfo.retType = params.functions[funcIndex].rtnType - let funcParamDefine = '' - let funcParamUse = '' - let funcInfoParams = '' - let funcInfoParamTemp = '[paramName]: [paramType]; ' - // 判断函数有几个参数,依次给参数赋值 - for(let i = 0; i < funcInfo.params.length; i++) { - let funcInfoParamReplace = replaceAll(funcInfoParamTemp, '[paramName]', funcInfo.params[i].name) - funcInfoParamReplace = replaceAll(funcInfoParamReplace, '[paramType]', funcInfo.params[i].type) - funcInfoParams += funcInfoParamReplace - let testType = getTestType(funcInfo.params[i].type); - if (testType === 'int') { - funcParamDefine += util.format('let %s = %s\n ', funcInfo.params[i].name, generateRandomInteger(0, LENGTH)) - funcParamUse += funcInfo.params[i].name + ', ' - } else if (testType === 'float') { - funcParamDefine += util.format('let %s = %s\n ', funcInfo.params[i].name, generateRandomArbitrary(0, LENGTH, TWO_DECIMAL)) - funcParamUse += funcInfo.params[i].name + ', ' - } else if (testType === 'bool') { - funcParamDefine += util.format('let %s = %s\n ', funcInfo.params[i].name, generateRandomBoolValue()) - funcParamUse += funcInfo.params[i].name + ', ' - } else if (testType === 'string') { - funcParamDefine += util.format('let %s = "%s"\n ', funcInfo.params[i].name, generateRandomString(LENGTH)) - funcParamUse += funcInfo.params[i].name + ', ' - } else if (TypeList.getValue(testType)) { - let typeDefineRes = getTypeDefine(testType, funcParamDefine, funcInfo, i, funcParamUse); - funcParamDefine = typeDefineRes[0] - funcParamUse = typeDefineRes[1] - } else if (InterfaceList.getBody(testType)) { - let interfaceDefineRes = getInterfaceDefine(testType, funcParamDefine, funcInfo, i, funcParamUse); - funcParamDefine = interfaceDefineRes[0] - funcParamUse = interfaceDefineRes[1] - } - } - // 去除调用参数的最后一个',' - let index = funcParamUse.lastIndexOf(', '); - funcParamUse = funcParamUse.substring(0, index); - let callFunc = '' - let hilogContent = '' - // 调用函数 - if (getJsType(funcInfo.retType) !== 'void') { - callFunc = util.format('let result: %s = testNapi.%s(%s)\n ', getJsType(funcInfo.retType), tsFuncName, funcParamUse) - // 加 hilog 打印 - hilogContent = util.format('hilog.info(0x0000, "testTag", "Test NAPI %s: ", JSON.stringify(result));\n ', tsFuncName) - hilogContent += util.format('console.info("testTag", "Test NAPI %s: ", JSON.stringify(result));\n ', tsFuncName) - } else { - callFunc = util.format('testNapi.%s(%s)\n ', tsFuncName, funcParamUse) - } - let func_test_replace = funcParamDefine + callFunc + hilogContent - // 替换test_case_name - let funcTestContent = replaceAll(abilityTestTemplete,'[func_direct_testCase]', func_test_replace) - funcTestContent = replaceAll(funcTestContent, '[test_case_name]', tsFuncName) - funcTestContent = replaceAll(funcTestContent, '[file_introduce_replace]', hFileName) - funcTestContent = replaceAll(funcTestContent, '[func_introduce_replace]', funcInfo.name) - funcTestContent = replaceAll(funcTestContent, '[input_introduce_replace]', funcInfoParams === ''? 'void': funcInfoParams) - funcTestContent = replaceAll(funcTestContent, '[output_introduce_replace]', funcInfo.retType) - - return funcTestContent -} - -function getTypeDefine(testType, funcParamDefine, funcInfo, i, funcParamUse) { - let typeDefType = TypeList.getValue(testType); - // genType - if (typeDefType === 'number') { - funcParamDefine += util.format('let %s = %s\n ', funcInfo.params[i].name, generateRandomInteger(0, LENGTH)); - funcParamUse += funcInfo.params[i].name + ', '; - } else if (typeDefType === 'string') { - funcParamDefine += util.format('let %s = "%s"\n ', funcInfo.params[i].name, generateRandomString(LENGTH)); - funcParamUse += funcInfo.params[i].name + ', '; - } else if (typeDefType === 'boolean') { - funcParamDefine += util.format('let %s = %s\n ', funcInfo.params[i].name, generateRandomBoolValue()); - funcParamUse += funcInfo.params[i].name + ', '; - } - return [funcParamDefine, funcParamUse]; -} - -function getInterfaceDefine(testType, funcParamDefine, funcInfo, i, funcParamUse) { - let objValue = InterfaceList.getBody(testType); - let objTestData = 'let %s:testNapi.%s = { '; - for (let j = 0; j < objValue.length; j++) { - if (objValue[j].type === 'number') { - objTestData += util.format('%s: %s, ', objValue[j].name, generateRandomInteger(0, LENGTH)); - } else if (objValue[j].type === 'string') { - objTestData += util.format('%s: "%s", ', objValue[j].name, generateRandomString(LENGTH)); - } else if (objValue[j].type === 'boolean') { - objTestData += util.format('%s: %s, ', objValue[j].name, generateRandomBoolValue()); - } else if (InterfaceList.getBody(objValue[j].type)) { - objTestData += util.format('%s: null, ', objValue[j].name); - } else if (objValue[j].type.indexOf('=>') >= 0) { // 成员方法 - let interfaceFunc = objValue[j].type; - let indexFunc = interfaceFunc.indexOf('=>'); - let interfaceFuncRet = interfaceFunc.substring(indexFunc + 2, interfaceFunc.length); - if (interfaceFuncRet.trim() === 'void') { - let interfaceFuncRetDefine = interfaceFunc.substring(0, indexFunc + 2) + '{}'; - objTestData += util.format('%s, ', interfaceFuncRetDefine); - } else if (interfaceFuncRet.trim() === 'string') { - let interfaceFuncRetDefine = interfaceFunc.substring(0, indexFunc + 2) + '{return ""}'; - objTestData += util.format('%s, ', interfaceFuncRetDefine); - } else if (interfaceFuncRet.trim() === 'boolean') { - let interfaceFuncRetDefine = interfaceFunc.substring(0, indexFunc + 2) + '{ return true }'; - objTestData += util.format('%s, ', interfaceFuncRetDefine); - } else if (interfaceFuncRet.trim() === 'number') { - let interfaceFuncRetDefine = interfaceFunc.substring(0, indexFunc + 2) + '{ return 0 }'; - objTestData += util.format('%s, ', interfaceFuncRetDefine); - } - } - } - - // 去除调用参数的最后一个',' - let index = objTestData.lastIndexOf(', '); - if (index !== -1) { - objTestData = objTestData.substring(0, index) + ' }\n '; - } else { - objTestData = 'let %s:testNapi.%s = null;\n '; - } - funcParamDefine += util.format(objTestData, funcInfo.params[i].name, testType); - funcParamUse += funcInfo.params[i].name + ', '; - return [funcParamDefine, funcParamUse]; -} - -function replaceAll(s, sfrom, sto) { - while (s.indexOf(sfrom) >= 0) { - s = s.replace(sfrom, sto) - } - return s; -} - -function getTestType(type) { - // 去掉const 和 * - type = type.replaceAll('const', '').replaceAll('*', '').trim() - if (type === 'uint32_t' || type === 'int32_t' || type === 'int16_t' || - type === 'int64_t' || type === 'int' || type === 'size_t') { - return 'int' - } else if (type === 'double_t' || type === 'double' || type === 'float') { - return 'float' - } else if (type === 'bool') { - return 'bool' - } else if (type === 'std::string' || type.indexOf('char') >= 0) { - return 'string' - } - return type -} - -function getJsType(type) { - // 去掉const 和 * - type = type.replaceAll('const', '').replaceAll('*', '').trim() - if (type === 'uint32_t' || type === 'int32_t' || type === 'int16_t' || type === 'int64_t' || - type === 'int' || type === 'double_t' || type === 'double' || type === 'float' || type === 'size_t') { - return 'number' - } else if (type.indexOf('char') >= 0 || type === 'std::string') { - return 'string' - } else if (type === 'bool') { - return 'boolean' - } else if (type === 'void') { - return type - } else { - // 对象,在ts中定义为interface - return 'testNapi.' + type.replace('*', '').trim() - } -} - -function createParam(parseParamInfo) { - let param = { - "name": "", - "type": "" - } - param.name = parseParamInfo.name - param.type = parseParamInfo.type - return param -} - -module.exports = { - generateFuncTestCase -} \ No newline at end of file -- Gitee From 88a0ca6a35bffff8e3ff35e91d9571b7f6e8d654 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:45:41 +0800 Subject: [PATCH 38/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/tools/NapiLog.js=20=E5=88=A0=E9=99=A4examples/na?= =?UTF-8?q?pitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAj?= =?UTF-8?q?s=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../tool/commandLine/src/tools/NapiLog.js | 138 ------------------ 1 file changed, 138 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/tools/NapiLog.js diff --git a/examples/napitutorials/tool/commandLine/src/tools/NapiLog.js b/examples/napitutorials/tool/commandLine/src/tools/NapiLog.js deleted file mode 100644 index 6089bb64..00000000 --- a/examples/napitutorials/tool/commandLine/src/tools/NapiLog.js +++ /dev/null @@ -1,138 +0,0 @@ -/* -* Copyright (c) 2024 Shenzhen Kaihong Digital Industry Development Co., Ltd. -* Licensed under the Apache License, Version 2.0 (the "License"); -* you may not use this file except in compliance with the License. -* You may obtain a copy of the License at -* -* http://www.apache.org/licenses/LICENSE-2.0 -* -* Unless required by applicable law or agreed to in writing, software -* distributed under the License is distributed on an "AS IS" BASIS, -* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -* See the License for the specific language governing permissions and -* limitations under the License. -*/ -const fs = require('fs'); -const path = require("path"); -let vscode = null; -try { - vscode = require('vscode'); -} -catch (err) { - vscode = null; -} - -class NapiLog { - constructor() { - } -} -NapiLog.LEV_NONE = 0; -NapiLog.LEV_ERROR = 1; -NapiLog.LEV_DEBUG = 2; -NapiLog.LEV_INFO = 3; - -const LEV_STR = ["[NON]", "[ERR]", "[DBG]", "[INF]"] -var logLevel = NapiLog.LEV_ERROR; -var logFileName = null; -var logResultMessage = [true, ""] - -function getDateString() { - let nowDate = new Date(); - return nowDate.toLocaleString(); -} - -function saveLog(dateStr, levStr, detail) { - if (logFileName) { - let logStr = dateStr + " " + levStr + " " + detail + "\n"; - fs.appendFileSync(logFileName, logStr); - } -} - -NapiLog.init = function (level, fileName) { - logLevel = level in [NapiLog.LEV_NONE, NapiLog.LEV_ERROR, NapiLog.LEV_DEBUG, NapiLog.LEV_INFO] - ? level : NapiLog.LEV_ERROR; - logFileName = fileName ? fileName : "napi_generator.log"; -} - -/** - * 通过调用栈获取当前正在执行的方法名,代码行数及文件路径 - * @param {} callerFuncName 指定取调用栈中哪个方法名所在的帧作为目标帧 - * @returns - */ -NapiLog.getCallPath = function(callerFuncName = null) { - let callPath = "" - let stackArray = new Error().stack.split('\n'); - - // 如果没有指定目标方法,默认在调用栈中查找当前方法"getCallPath"所在的帧 - let destFuncName = callerFuncName != null ? callerFuncName : "getCallPath" - - for (let i = stackArray.length -1; i >=0 ; --i) { - // debug模式和打包后的可执行程序调用栈函数名不同, 以NapiLog.log()方法为例: - // vscode debug模式下调用栈打印的方法名为NapiLog.log,而可执行程序的调用栈中显示为Function.log() - let callerMatch = (stackArray[i].indexOf("NapiLog." + destFuncName) > 0 - || stackArray[i].indexOf("Function." + destFuncName) > 0) - if (callerMatch) { - let stackMsg = stackArray[i+1].trim() - let leftIndex = stackMsg.indexOf("(") - let rightIndex = stackMsg.indexOf(")") - - if (leftIndex > 0 && rightIndex > 0) { - let funInfo = stackMsg.substring(0, leftIndex); - let srcPath = stackMsg.substring(leftIndex + 1, rightIndex) - let colNumIndex = srcPath.lastIndexOf(":") - let colNum = srcPath.substring(colNumIndex + 1, srcPath.length) - let lineNumIndex = srcPath.lastIndexOf(":", colNumIndex - 1) - let lineNum = srcPath.substring(lineNumIndex + 1, colNumIndex) - let filePath = srcPath.substring(0, lineNumIndex) - - callPath = "%s[%s(%s:%s)]".format(funInfo,filePath,lineNum,colNum) - } - break; - } - } - - return callPath; -} - -function print(...args) { - if (vscode) { - vscode.window.showInformationMessage(...args); - } - console.log(args + ""); -} - -function recordLog(lev, ...args) { - let origMsgInfo = args; - let callPath = NapiLog.getCallPath("log"); - let dataStr = getDateString(); - let detail = args.join(" "); - saveLog(dataStr + " " + callPath, LEV_STR[lev], detail); - if (lev === NapiLog.LEV_ERROR) { - logResultMessage = [false, detail]; - } - let logStr = callPath + " " + detail; - if (logLevel <= lev) return logStr; - NapiLog.logInfo(origMsgInfo[0]); - return logStr; -} - -NapiLog.logError = function (...args) { - let logInfo = recordLog(NapiLog.LEV_ERROR, args); - print(logInfo); -} - -NapiLog.logDebug = function (...args) { - recordLog(NapiLog.LEV_DEBUG, args); -} - -NapiLog.logInfo = function (...args) { - recordLog(NapiLog.LEV_INFO, args); -} - -NapiLog.getResult = function () { - return logResultMessage; -} - -module.exports = { - NapiLog -} \ No newline at end of file -- Gitee From 6a38a9ddcb4f283a5d55489480c499b8f1799d26 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:46:15 +0800 Subject: [PATCH 39/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/tools/Tool.js=20=E5=88=A0=E9=99=A4examples/napit?= =?UTF-8?q?utorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs?= =?UTF-8?q?=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../tool/commandLine/src/tools/Tool.js | 175 ------------------ 1 file changed, 175 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/tools/Tool.js diff --git a/examples/napitutorials/tool/commandLine/src/tools/Tool.js b/examples/napitutorials/tool/commandLine/src/tools/Tool.js deleted file mode 100644 index 8a0f3495..00000000 --- a/examples/napitutorials/tool/commandLine/src/tools/Tool.js +++ /dev/null @@ -1,175 +0,0 @@ -/* -* Copyright (c) 2024 Shenzhen Kaihong Digital Industry Development Co., Ltd. -* Licensed under the Apache License, Version 2.0 (the "License"); -* you may not use this file except in compliance with the License. -* You may obtain a copy of the License at -* -* http://www.apache.org/licenses/LICENSE-2.0 -* -* Unless required by applicable law or agreed to in writing, software -* distributed under the License is distributed on an "AS IS" BASIS, -* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -* See the License for the specific language governing permissions and -* limitations under the License. -*/ -const fs = require('fs'); -const MOVE_EIGHTEEN = 18; -const MOVE_TWELVE = 12; -const MOVE_SIX = 6; - -function utf8ArrayToStr(array) { - let char2, char3; - - let outStr = ""; - let len = array.length; - let i = 0; - while (i < len) { - let ch = array[i++]; - switch (ch >> 4) { - case 0: case 1: case 2: case 3: case 4: case 5: case 6: case 7: - // 0xxxxxxx - outStr += String.fromCharCode(ch); - break; - case 12: case 13: - // 110x xxxx 10xx xxxx - char2 = array[i++]; - outStr += String.fromCharCode(((ch & 0x1F) << 6) | (char2 & 0x3F)); - break; - case 14: - // 1110 xxxx 10xx xxxx 10xx xxxx - char2 = array[i++]; - char3 = array[i++]; - outStr += String.fromCharCode(((ch & 0x0F) << 12) | - ((char2 & 0x3F) << 6) | - ((char3 & 0x3F) << 0)); - break; - } - } - - return outStr; -} - -function stringToUint8Array(string, option = { streamBool: false }) { - if (option.streamBool) { - throw new Error(`Failed to encode: the 'streamBool' option is unsupported.`); - } - const len = string.length; - let position = 0; - // output position - let atPos = 0; - // 1.5x size - let tlength = Math.max(32, len + (len >> 1) + 7); - // ... but atPos 8 byte offset - let target = new Uint8Array((tlength >> 3) << 3); - - while (position < len) { - let value = string.charCodeAt(position++); - let isContinue = false; - if (value >= 0xd800 && value <= 0xdbff) { - if (position < len) {// high surrogate - const extra = string.charCodeAt(position); - if ((extra & 0xfc00) === 0xdc00) { - ++position; - value = ((value & 0x3ff) << 10) + (extra & 0x3ff) + 0x10000; - } - } - if (value >= 0xd800 && value <= 0xdbff) { - isContinue = true; // drop lone surrogate - } - } - - if (!isContinue) { - // expand the buffer if we couldn't write 4 bytes - if (atPos + 4 > target.length) { - tlength += 8; // minimum extra - tlength *= (1.0 + (position / string.length) * 2); // take 2x the remaining - tlength = (tlength >> 3) << 3; // 8 byte offset - - target = uint8Array(tlength, target); - } - - let calculateResult = calculate(value, target, atPos) - isContinue = calculateResult[0] - target = calculateResult[1] - atPos = calculateResult[2] - } - } - return target.slice(0, atPos); -} - -function calculate(val, target, at) { - let isContinue = false - if ((val & 0xffffff80) === 0) { // 1-byte - target[at++] = val; // ASCII - isContinue = true; - } else if ((val & 0xffe00000) === 0) { // 4-byte - target[at++] = ((val >> MOVE_EIGHTEEN) & 0x07) | 0xf0; - target[at++] = ((val >> MOVE_TWELVE) & 0x3f) | 0x80; - target[at++] = ((val >> MOVE_SIX) & 0x3f) | 0x80; - } else if ((val & 0xffff0000) === 0) { // 3-byte - target[at++] = ((val >> MOVE_TWELVE) & 0x0f) | 0xe0; - target[at++] = ((val >> MOVE_SIX) & 0x3f) | 0x80; - } else if ((val & 0xfffff800) === 0) { // 2-byte - target[at++] = ((val >> MOVE_SIX) & 0x1f) | 0xc0; - } else { - isContinue = true; - } - if (!isContinue) { - target[at++] = (val & 0x3f) | 0x80; - } - return [isContinue, target, at] -} - -function uint8Array(tlen, target) { - const update = new Uint8Array(tlen); - update.set(target); - return update -} - -function readFile(fn) { - if (!fs.existsSync(fn)) { - return ""; - } - let data = fs.readFileSync(fn); - data = utf8ArrayToStr(data); - return data; -} - -function writeFile(fn, str) { - fs.writeFileSync(fn, str, { encoding: 'utf8' }); -} - -function appendWriteFile(fn, str) { - fs.appendFile(fn, str, 'utf8', err => { - if (err) { - console.error(err); - return; - } - }); -} - -// 随机生成整数 -function generateRandomInteger(min, max) { - min = Math.ceil(min); - max = Math.floor(max); - return Math.floor(Math.random() * (max - min + 1)) + min; -} - -/** - * 获取Json文件内容 - * @returns - */ -function getJsonCfg(jsonFilePath) { - let jsonCfg = null; // json 配置文件 - let jsonFile = fs.readFileSync(jsonFilePath, { encoding: "utf8" }); - jsonCfg = JSON.parse(jsonFile); - return jsonCfg; -} - -module.exports = { - readFile, - writeFile, - appendWriteFile, - generateRandomInteger, - getJsonCfg -} \ No newline at end of file -- Gitee From aef17371152afe232738f14ffec376958145c07a Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:47:16 +0800 Subject: [PATCH 40/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/tools/common.js=20=E5=88=A0=E9=99=A4examples/nap?= =?UTF-8?q?itutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs?= =?UTF-8?q?=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../tool/commandLine/src/tools/common.js | 76 ------------------- 1 file changed, 76 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/tools/common.js diff --git a/examples/napitutorials/tool/commandLine/src/tools/common.js b/examples/napitutorials/tool/commandLine/src/tools/common.js deleted file mode 100644 index 38d732db..00000000 --- a/examples/napitutorials/tool/commandLine/src/tools/common.js +++ /dev/null @@ -1,76 +0,0 @@ -/* -* Copyright (c) 2024 Shenzhen Kaihong Digital Industry Development Co., Ltd. -* Licensed under the Apache License, Version 2.0 (the "License"); -* you may not use this file except in compliance with the License. -* You may obtain a copy of the License at -* -* http://www.apache.org/licenses/LICENSE-2.0 -* -* Unless required by applicable law or agreed to in writing, software -* distributed under the License is distributed on an "AS IS" BASIS, -* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -* See the License for the specific language governing permissions and -* limitations under the License. -*/ - -class InterfaceList { } -InterfaceList.interfacess_ = []; -InterfaceList.push = function (ifs) { - InterfaceList.interfacess_.push(ifs) -} -InterfaceList.pop = function () { - InterfaceList.interfacess_.pop() -} -InterfaceList.getValue = function (name) { - let ifs = InterfaceList.interfacess_ - for (let i in ifs) { - if (ifs[i].name === name) { - var hasProperty = Object.prototype.hasOwnProperty.call(ifs[i].body, "allProperties") - if (hasProperty) { - return ifs[i].body.allProperties.values; - } else { - return ifs[i].body.value; - } - } - } - return null; -} - -InterfaceList.getBody = function (name) { - let ifs = InterfaceList.interfacess_ - for (let i in ifs) { - if (ifs[i].name === name) { - return ifs[i].body; - } - } - return null; -} - -class TypeList { } -TypeList.types = []; -TypeList.push = function (ifs) { - TypeList.types.push(ifs) -} -TypeList.pop = function () { - TypeList.types.pop() -} -TypeList.getValue = function (name) { - // let ifs = TypeList.types[TypeList.types.length - 1] - let ifs = TypeList.types - for (let i in ifs) { - if (ifs[i].name === name) { - var hasProperty = Object.prototype.hasOwnProperty.call(ifs[i].body, "allProperties") - if (hasProperty) { - return ifs[i].body.allProperties.values; - } else { - return ifs[i].body; - } - } - } - return null; -} - -module.exports = { - InterfaceList, - TypeList, -} \ No newline at end of file -- Gitee From 3594464e297fdd0f605e13e857c2a0fc38ece207 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:48:01 +0800 Subject: [PATCH 41/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/tools/commonTemplete.js=20=E5=88=A0=E9=99=A4exam?= =?UTF-8?q?ples/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../commandLine/src/tools/commonTemplete.js | 103 ------------------ 1 file changed, 103 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/tools/commonTemplete.js diff --git a/examples/napitutorials/tool/commandLine/src/tools/commonTemplete.js b/examples/napitutorials/tool/commandLine/src/tools/commonTemplete.js deleted file mode 100644 index fae07ab4..00000000 --- a/examples/napitutorials/tool/commandLine/src/tools/commonTemplete.js +++ /dev/null @@ -1,103 +0,0 @@ -/* -* Copyright (c) 2022 Shenzhen Kaihong Digital Industry Development Co., Ltd. -* Licensed under the Apache License, Version 2.0 (the "License"); -* you may not use this file except in compliance with the License. -* You may obtain a copy of the License at -* -* http://www.apache.org/licenses/LICENSE-2.0 -* -* Unless required by applicable law or agreed to in writing, software -* distributed under the License is distributed on an "AS IS" BASIS, -* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -* See the License for the specific language governing permissions and -* limitations under the License. -*/ -const { writeFile } = require("./Tool"); -const re = require("./re"); - -let commonH = ` -#ifndef [h_define_replace] -#define [h_define_replace] - -#include -#include -#include -#include -#include -#include "hilog/log.h" -#include "napi/native_api.h" -#include "[business_include_replace]" - -#define GLOBAL_RESMGR (0xFFEE) -const unsigned int LOG_PRINT_DOMAIN = 0xFF00; - -constexpr int32_t STR_MAX_SIZES = 200; -constexpr int32_t LONG_STR_MAX_SIZES = 1024; -constexpr uint8_t PARAMS0 = 0; -constexpr uint8_t PARAMS1 = 1; -constexpr uint8_t PARAMS2 = 2; -constexpr uint8_t PARAMS3 = 3; -constexpr uint8_t PARAMS4 = 4; -constexpr uint8_t PARAMS5 = 5; -constexpr uint8_t PARAMS6 = 6; -constexpr uint8_t PARAMS7 = 7; -constexpr uint8_t PARAMS8 = 8; -constexpr uint8_t PARAMS9 = 9; -constexpr uint8_t PARAMS10 = 10; -constexpr uint8_t PARAMS11 = 11; -constexpr uint8_t PARAMS12 = 12; -constexpr uint8_t PARAMS100 = 100; - -void getErrMessage(napi_status &status, napi_env &env, const napi_extended_error_info *&extended_error_info, - const char *info, const char *tag); - -#endif //[h_define_replace] -` - -let commonCpp = ` -#include "[include_name]common.h" - -/*[NAPI_GEN]:错误处理,获取错误详细信息*/ -void getErrMessage(napi_status &status, napi_env &env, const napi_extended_error_info *&extended_error_info, - const char *info, const char *tag) -{ - status = napi_get_last_error_info(env, &extended_error_info); - if (status == napi_ok && extended_error_info != NULL) { - const char *errorMessage = - extended_error_info->error_message != NULL ? extended_error_info->error_message : "Unknown error"; - OH_LOG_Print(LOG_APP, LOG_ERROR, GLOBAL_RESMGR, tag, "errmsg %{public}s!, engine_err_code %{public}d!.", - std::to_string(extended_error_info->engine_error_code).c_str(), extended_error_info->error_code); - std::string myInfo = info; - std::string res = "Failed to " + myInfo + " em = " + errorMessage + - ", eec = " + std::to_string(extended_error_info->engine_error_code) + - ", ec = " + std::to_string(extended_error_info->error_code); - napi_throw_error(env, NULL, res.c_str()); - } -} -` - -function generateBase(destDir, license, hFilePath) { - let index = hFilePath.lastIndexOf("\\"); - let indexH = hFilePath.lastIndexOf(".h"); - let hFileName = hFilePath.substring(index + 1, indexH).toLowerCase(); - // [h_define_replace] - let hDefine = "NAPITUTORIALS_" + hFileName.toLocaleUpperCase() + "COMMON_H" - commonH = replaceAll(commonH, "[h_define_replace]", hDefine) - // [business_include_replace] - let businessInclude = hFilePath.substring(index + 1, hFilePath.length) - commonH = replaceAll(commonH, "[business_include_replace]", businessInclude) - commonCpp = replaceAll(commonCpp, "[include_name]", hFileName) - writeFile(re.pathJoin(destDir, hFileName + "common.h"), null != license ? (license + "\n" + commonH) : commonH) - writeFile(re.pathJoin(destDir, hFileName + "common.cpp"), null != license ? (license + "\n" + commonCpp): commonCpp) -} - -function replaceAll(s, sfrom, sto) { - while (s.indexOf(sfrom) >= 0) { - s = s.replace(sfrom, sto) - } - return s; -} - -module.exports = { - generateBase -} \ No newline at end of file -- Gitee From 9917b958e19080a10e49dd29d209e63dce172abf Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:49:27 +0800 Subject: [PATCH 42/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/tools/re.js=20=E5=88=A0=E9=99=A4examples/napitut?= =?UTF-8?q?orials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20h?= =?UTF-8?q?tml=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../tool/commandLine/src/tools/re.js | 80 ------------------- 1 file changed, 80 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/tools/re.js diff --git a/examples/napitutorials/tool/commandLine/src/tools/re.js b/examples/napitutorials/tool/commandLine/src/tools/re.js deleted file mode 100644 index 61385d14..00000000 --- a/examples/napitutorials/tool/commandLine/src/tools/re.js +++ /dev/null @@ -1,80 +0,0 @@ -/* -* Copyright (c) 2024 Shenzhen Kaihong Digital Industry Development Co., Ltd. -* Licensed under the Apache License, Version 2.0 (the "License"); -* you may not use this file except in compliance with the License. -* You may obtain a copy of the License at -* -* http://www.apache.org/licenses/LICENSE-2.0 -* -* Unless required by applicable law or agreed to in writing, software -* distributed under the License is distributed on an "AS IS" BASIS, -* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -* See the License for the specific language governing permissions and -* limitations under the License. -*/ -const path = require('path'); - -function search(ss, data) { - ss = replaceAll(ss, "\\.", "\\.") - let reg = new RegExp(ss); - let tt = reg.exec(data); - if (tt === null || tt === undefined) return null; - let ret = { "regs": [] } - for (let i = 0; i < tt.length; i++) { - let p = data.indexOf(tt[i]); - if (tt[i] === null || tt[i] === undefined) { - ret.regs.push([-1, -1]) - } - else { - ret.regs.push([p, p + tt[i].length]) - } - } - - return ret; -} - -function match(ss, data) { - let tt = search(ss, data) - if ((tt !== null && tt !== undefined) && tt.regs[0][0] === 0) return tt; - return null; -} - -function removeReg(data, reg) { - return data.substring(0, reg[0]) + data.substring(reg[1], data.length) -} - -function getReg(data, reg) { - return data.substring(reg[0], reg[1]) -} - -function getFileInPath(tpath) { - return path.parse(tpath).base; -} - -function getPathInPath(tpath) { - return path.parse(tpath).dir; -} - -function all(sfrom) { - return new RegExp(sfrom, "g"); -} - -function replaceAll(ss, sfrom, sto) { - return ss.replace(all(sfrom), sto) -} - -function pathJoin(...args) { - return path.join(...args) -} - -module.exports = { - search, - match, - removeReg, - getReg, - getFileInPath, - getPathInPath, - pathJoin, - replaceAll, - all -} \ No newline at end of file -- Gitee From 7a5dda2868ed7c90d308de4835d72dabcbb55a23 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:50:50 +0800 Subject: [PATCH 43/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/tsGen/header=5Fparser.py=20=E5=88=A0=E9=99=A4exa?= =?UTF-8?q?mples/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../commandLine/src/tsGen/header_parser.py | 24 ------------------- 1 file changed, 24 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/tsGen/header_parser.py diff --git a/examples/napitutorials/tool/commandLine/src/tsGen/header_parser.py b/examples/napitutorials/tool/commandLine/src/tsGen/header_parser.py deleted file mode 100644 index 125e36a5..00000000 --- a/examples/napitutorials/tool/commandLine/src/tsGen/header_parser.py +++ /dev/null @@ -1,24 +0,0 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -# Copyright (c) 2024 Shenzhen Kaihong Digital Industry Development Co., Ltd. -# -# HDF is dual licensed: you can use it either under the terms of -# the GPL, or the BSD license, at your option. -# See the LICENSE file in the root of this repository for complete details. - -import json -import sys -import CppHeaderParser - -if __name__ == "__main__": - fileName = sys.argv[1]; - try: - hjson = json.loads(CppHeaderParser.CppHeader(fileName).toJSON()) - print(json.dumps({ - "result": hjson - })) - except CppHeaderParser.CppParseError: - print(CppHeaderParser.CppParseError) - finally: - pass \ No newline at end of file -- Gitee From c7f598b761d3ddb2823ab38cceb58eb724031803 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:51:36 +0800 Subject: [PATCH 44/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/c?= =?UTF-8?q?ommandLine/src/tsGen/tsMain.js=20=E5=88=A0=E9=99=A4examples/nap?= =?UTF-8?q?itutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAjs?= =?UTF-8?q?=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../tool/commandLine/src/tsGen/tsMain.js | 741 ------------------ 1 file changed, 741 deletions(-) delete mode 100644 examples/napitutorials/tool/commandLine/src/tsGen/tsMain.js diff --git a/examples/napitutorials/tool/commandLine/src/tsGen/tsMain.js b/examples/napitutorials/tool/commandLine/src/tsGen/tsMain.js deleted file mode 100644 index 67791de4..00000000 --- a/examples/napitutorials/tool/commandLine/src/tsGen/tsMain.js +++ /dev/null @@ -1,741 +0,0 @@ -/* -* Copyright (c) 2024 Shenzhen Kaihong Digital Industry Development Co., Ltd. -* Licensed under the Apache License, Version 2.0 (the "License"); -* you may not use this file except in compliance with the License. -* You may obtain a copy of the License at -* -* http://www.apache.org/licenses/LICENSE-2.0 -* -* Unless required by applicable law or agreed to in writing, software -* distributed under the License is distributed on an "AS IS" BASIS, -* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -* See the License for the specific language governing permissions and -* limitations under the License. -*/ -const { NapiLog } = require("../tools/NapiLog"); -const { writeFile, appendWriteFile, generateRandomInteger, readFile, getJsonCfg } = require("../tools/Tool"); -const path = require('path') -const re = require("../tools/re"); -const fs = require("fs"); -const os = require("os"); -const util = require('util'); -const readline = require('readline'); -const { generateDirectFunction } = require('../napiGen/functionDirect') -const { generateFuncTestCase } = require('../napiGen/functionDirectTest') -const { generateBase } = require('../tools/commonTemplete') -const { InterfaceList, TypeList } = require('../tools/common') - -const MIN_RANDOM = 100 -const MAX_RANDOM = 999 -let tsFuncName = '' - -function parseFileAll(hFilePath) { - let execSync = require("child_process").execSync - let cmd = "" - - // call exe file (for real runtime) - let sysInfo = os.platform() - let execPath = path.dirname(process.execPath) - // console.info("execPath : " + execPath) - let exeFile = sysInfo === 'win32' ? path.join(execPath, "header_parser.exe") : - path.join(execPath, "header_parser") - cmd = exeFile + " " + hFilePath - - let parseResult = null - let stdout = execSync(cmd) - parseResult = JSON.parse(stdout.toString()).result - return parseResult -} - -function createNameSpaceInfo(parseNameSpaceInfo) { - let nameSpaceInfo = { - "name": "", - "classes": [], - "functions": [] - } - nameSpaceInfo.name = parseNameSpaceInfo - return nameSpaceInfo -} - -function analyzeNameSpace(rootInfo, parseResult) { - let parseNameSpaces = parseResult.namespaces - for (var i = 0; i < parseNameSpaces.length; ++i) { - let nameSpaceInfo = createNameSpaceInfo(parseNameSpaces[i]) - rootInfo.namespaces.push(nameSpaceInfo) - } -} - -function isStringType(cType) { - switch (cType) { - case 'string': - case 'std::string': - case 'char': - case 'wchar_t': - case 'char16_t': - case 'char32_t': - return true - default: - return false - } -} - -function isBoolType(cType) { - if (cType === 'bool') { - return true - } - return false -} - -function isNumberType(cType) { - switch (cType) { - case 'short': - case 'int': - case 'uint32_t': - case 'size_t': - case 'long': - case 'long long': - case 'float': - case 'double': - case 'long double': - case 'int16_t': - case 'uint16_t': - case 'int32_t': - case 'int64_t': - case 'uint64_t': - case 'double_t': - case 'float_t': - return true - default: - return false - } -} - -function basicC2js(cType) { - let jsType = "" - if (isStringType(cType)) { - jsType = 'string' - } else if (isBoolType(cType)) { - jsType = 'boolean' - } else if (isNumberType(cType)) { - jsType = 'number' - } else { - jsType = cType - } - return jsType -} - -function getJsTypeFromC(cType, typeInfo) { - let basicCtype = cType - let matchs = re.match("(std::)?vector<([\x21-\x7e ]+)>", basicCtype); - if (matchs) { - basicCtype = re.getReg(basicCtype, matchs.regs[2]).trim() - typeInfo.array = 1 - } - - let unsignedIdx = basicCtype.indexOf('unsigned') - if (unsignedIdx >= 0) { - // cut off the keywords 'unsigned' - basicCtype = basicCtype.substring(unsignedIdx + 8, basicCtype.length).trim() - } - let jsType = basicCtype - if (typeInfo.array) { - jsType = util.format("Array<%s>", jsType) - } - // 去掉const - jsType = jsType.replaceAll('const', '') - // struct cJson * 的情况 - let matchStruct = re.match("(struct)?[A-Z_a-z0-9 *]+", basicCtype); - if (matchStruct) { - let index = basicCtype.indexOf('struct') - // 去掉struct和* - if (index >=0) { - jsType = jsType.substring(index + 6, basicCtype.length) - } - jsType = jsType.replaceAll('*', '').trim() - } - jsType = basicC2js(jsType) - return jsType -} - -function createParam(parseParamInfo) { - let param = { - "name": "", - "type": "" - } - param.name = parseParamInfo.name - let rawType = getJsTypeFromC(parseParamInfo.type, parseParamInfo) - param.type = rawType - - return param -} - -function createFuncInfo(parseFuncInfo, isClassFunc) { - let funcInfo = { - "name": "", - "genName": "", - "params": [], - "namespace": "", - "retType": "", - "static": "" - } - funcInfo.name = parseFuncInfo.name - funcInfo.namespace = parseFuncInfo.namespace - let tokenIndex = funcInfo.namespace.indexOf('::') - if (tokenIndex >= 0) { - // delete '::' in namespace, get the pure space name. - funcInfo.namespace = funcInfo.namespace.substring(0, tokenIndex) - } - - let parseParams = parseFuncInfo.parameters - // console.info("parseParams: " + JSON.stringify(parseParams)) - for (var i = 0; i < parseParams.length; ++i) { - let param = createParam(parseParams[i]) - funcInfo.params.push(param) - } - - funcInfo.isClassFunc = isClassFunc - - if (parseFuncInfo.static && isClassFunc) { - funcInfo.static = "static " - } - let retType = parseFuncInfo.returns === '' ? parseFuncInfo.rtnType : parseFuncInfo.returns - funcInfo.retType = getJsTypeFromC(retType, parseFuncInfo) - return funcInfo -} - -function putFuncIntoNamespace(funcInfo, namespaces) { - for (var i = 0; i < namespaces.length; ++i) { - if (namespaces[i].name === funcInfo.namespace) { - namespaces[i].functions.push(funcInfo) - return - } - } - // NapiLog.logError('The namespace [%s] of function %s is not found.'.format(funcInfo.namespace, funcInfo.name)); -} - -function analyzeRootTypeDef(rootInfo, parseResult) { - let parserTypedefs = Object.keys(parseResult.typedefs) - - for (let i = 0; i < parserTypedefs.length; ++i) { - let objTypedefKeys = parserTypedefs[i] - let objTypedefVal = parseResult.typedefs[parserTypedefs[i]] - rootInfo.typedefs.push({objTypedefKeys, objTypedefVal}) - } -} - -function analyzeRootFunction(rootInfo, parseResult) { - let parseFunctions = parseResult.functions - // console.info("parseFunctions: " + JSON.stringify(parseFunctions)) - for (var i = 0; i < parseFunctions.length; ++i) { - // 普通方法生成模板 - let funcInfo = createFuncInfo(parseFunctions[i], false) - //rootInfo.functions.push(funcInfo) - if (parseFunctions[i].namespace != '') { - // function in namespace - putFuncIntoNamespace(funcInfo, rootInfo.namespaces) - } else { - // function without namespace, put on root - rootInfo.functions.push(funcInfo) - } - } -} - -function createProperties(parseProperties) { - let propertyList = [] - for (var i = 0; i < parseProperties.length; ++i) { - let property = {} - property.name = parseProperties[i].name - property.type = getJsTypeFromC(parseProperties[i].type, parseProperties[i]) - propertyList.push(property) - } - return propertyList -} - -function createClassFunctions(parseFuncs) { - let funcList = [] - for (var i = 0; i < parseFuncs.length; ++i) { - let funcInfo = createFuncInfo(parseFuncs[i], true) - funcList.push(funcInfo) - } - return funcList -} - -function createClassInfo(parseClassInfo) { - let classInfo = { - "name": "", - "namespace": "", - "properties": [], - "functions": [], - "extends": [] - } - classInfo.name = parseClassInfo.name - classInfo.namespace = parseClassInfo.namespace - classInfo.properties = createProperties(parseClassInfo.properties.public) - classInfo.functions = createClassFunctions(parseClassInfo.methods.public) - - return classInfo -} - -function putClassIntoNamespace(classInfo, namespaces) { - for (var i = 0; i < namespaces.length; ++i) { - if (namespaces[i].name === classInfo.namespace) { - namespaces[i].classes.push(classInfo) - return - } - } - // NapiLog.logError('The namespace [%s] of class %s is not found.'.format(classInfo.namespace, classInfo.name)); -} - -function analyzeClasses(rootInfo, parseResult) { - let parseClasses = parseResult.classes; - - for (var className in parseClasses) { - let classInfo = createClassInfo(parseClasses[className]) - if (classInfo.namespace != '') { - // class in namespace - putClassIntoNamespace(classInfo, rootInfo.namespaces) - } else { - // class without namespace, put on root - rootInfo.classes.push(classInfo) - } - } -} - -function getTab(tabLv) { - let tab = "" - for (var i = 0; i < tabLv; ++i) { - tab += " " - } - return tab -} - -function genFunction(func, tabLv, dtsDeclare) { - let tab = getTab(tabLv) - let funcPrefix = func.isClassFunc ? "" : "export const " - let funcParams = "" - for (var i = 0; i < func.params.length; ++i) { - funcParams += i > 0 ? ", " : "" - funcParams += func.params[i].name + ": " + func.params[i].type - } - func.genName = 'KH' + generateRandomInteger(MIN_RANDOM, MAX_RANDOM) + '_' + func.name - let dtsDeclareContent = replaceAll(dtsDeclare, '[tab_replace]', tab) - dtsDeclareContent = replaceAll(dtsDeclareContent, '[export_replace]', funcPrefix) - dtsDeclareContent = replaceAll(dtsDeclareContent, '[func_name_replace]', func.genName) - dtsDeclareContent = replaceAll(dtsDeclareContent, '[func_param_replace]', funcParams) - dtsDeclareContent = replaceAll(dtsDeclareContent, '[input_introduce_replace]', funcParams === ''? "void": funcParams) - dtsDeclareContent = replaceAll(dtsDeclareContent, '[func_return_replace]', func.retType) - dtsDeclareContent = replaceAll(dtsDeclareContent, '[output_introduce_replace]', func.retType) - dtsDeclareContent = replaceAll(dtsDeclareContent, '[func_introduce_replace]', func.name) - - let classFuncTestUseTemplete = '[func_name_replace]:([func_param_replace]) => [func_return_replace]' - let classFuncTestUse = replaceAll(classFuncTestUseTemplete, '[func_name_replace]', func.genName) - classFuncTestUse = replaceAll(classFuncTestUse, '[func_param_replace]', funcParams) - classFuncTestUse = replaceAll(classFuncTestUse, '[func_return_replace]', func.retType) - let interfaceFuncResult = null; - if (func.isClassFunc) { - interfaceFuncResult = { - name: func.genName, - type: classFuncTestUse, - } - } - return [dtsDeclareContent,interfaceFuncResult] -} - -function isJsBasicType(type) { - if (type === 'number' || type === 'string' || type === 'boolean') { - return true; - } else { - return false; - } -} - -function genClass(classInfo, tabLv, dtsDeclare, needDeclare = false) { - let tab = getTab(tabLv) - let tsClass = tab + 'export ' + "interface " + classInfo.name + " {\n" - let tab1 = getTab(tabLv + 1) - let interfaceBody = []; - for (var i = 0; i < classInfo.properties.length; ++i) { - let myType = classInfo.properties[i].type - if (!isJsBasicType(myType)) { - myType += ' | null' - } - tsClass += util.format("%s%s: %s;\n", tab1, classInfo.properties[i].name, myType) - interfaceBody.push({ - name: classInfo.properties[i].name, - type: classInfo.properties[i].type, - }) - } - - // 循环加入class中的方法 - let interfaceFunc = null - for (let i = 0; i < classInfo.functions.length; ++i) { - let result = genFunction(classInfo.functions[i], tabLv+1, dtsDeclare); - tsClass += result[0] - interfaceFunc = result[1] - if (interfaceFunc !== null) { - interfaceBody.push(interfaceFunc) - } - } - tsClass += tab + "}\n" - - let interfaceData = { - name: classInfo.name, - body: interfaceBody - } - InterfaceList.push(interfaceData) - return tsClass -} - -function genNamespace(namespace, tabLv, dtsDeclare) { - let tab = getTab(tabLv) - let tsNamespace = tab + util.format("declare namespace %s {\n", namespace.name) - for (var i = 0; i < namespace.functions.length; ++i) { - tsNamespace += genFunction(namespace.functions[i], tabLv + 1 , dtsDeclare)[0] - } - for (var i = 0; i < namespace.classes.length; ++i) { - tsNamespace += genClass(namespace.classes[i], tabLv + 1, dtsDeclare) - } - tsNamespace += tab + "}\n" - return tsNamespace -} - -function genType(typeInfo, tabLv) { - let tab = getTab(tabLv) - let tsTypedef = '' - for (let i = 0; i < typeInfo.length; i++) { - if (isNumberType(typeInfo[i].objTypedefVal)) { - tsTypedef += tab + 'type ' + typeInfo[i].objTypedefKeys + ' = number;\n' - let typeData = { - name: typeInfo[i].objTypedefKeys, - body: "number" - } - TypeList.push(typeData) - } else if (isBoolType(typeInfo[i].objTypedefVal)) { - tsTypedef += tab + 'type ' + typeInfo[i].objTypedefKeys + ' = boolean;\n' - let typeData = { - name: typeInfo[i].objTypedefKeys, - body: "boolean" - } - TypeList.push(typeData) - } else if (isStringType(typeInfo[i].objTypedefVal)) { - tsTypedef += tab + 'type ' + typeInfo[i].objTypedefKeys + ' = string;\n' - let typeData = { - name: typeInfo[i].objTypedefKeys, - body: "string" - } - TypeList.push(typeData) - } - } - - return tsTypedef; -} - -function genTsContent(rootInfo, dtsDeclare) { - let tsContent = rootInfo.needCallback ? "import { AsyncCallback, Callback } from './../basic';\n\n" : "" - - // gen typedefs - tsContent += genType(rootInfo.typedefs, 0) - for (var i = 0; i < rootInfo.classes.length; ++i) { - tsContent += genClass(rootInfo.classes[i], 0, dtsDeclare, true) - } - - for (var i = 0; i < rootInfo.namespaces.length; ++i) { - tsContent += genNamespace(rootInfo.namespaces[i], 0, dtsDeclare) - } - - for (var i = 0; i < rootInfo.functions.length; ++i) { - tsContent += genFunction(rootInfo.functions[i], 0, dtsDeclare)[0] - } - - return tsContent -} - -function removeMarco(hFilePath, tempFilePath, macros) { - // 创建读取文件的流 - const fileStream = fs.createReadStream(hFilePath); - // 创建逐行读取的接口 - const rl = readline.createInterface({ - input: fileStream, - crlfDelay: Infinity - }); - // 存储处理后的文件内容 - let processedContent = ''; - // 逐行读取文件内容并处理 去除方法中的宏 - rl.on('line', (line) => { - // void *(CJSON_CDECL *malloc_fn)(size_t sz); - // CJSON_PUBLIC(const char*) cJSON_Version(void); - // 替换使用宏的地方,保留#define宏定义 - if (line.indexOf('#define') < 0 && line.indexOf('#ifndef') < 0 && line.indexOf('#ifdef') - && line.indexOf('#elif') && line.indexOf('#if') < 0 && line.indexOf('#else')) { - macros.forEach(macro => { - // 去掉使用的宏以及括号() - - let index = line.indexOf(macro) - if (index >= 0) { - let regexPattern = new RegExp(macro + '\\s*\\('); - let isMatch = regexPattern.test(line) - if (isMatch) { - let removeIndexLeft = line.indexOf('(') - line = line.substring(0, index) + line.substring(index + macro.length, removeIndexLeft) - + line.substring(removeIndexLeft + 1, line.length) - let removeIndexRight = line.indexOf(')') - line = line.substring(0, removeIndexRight) + line.substring(removeIndexRight + 1, line.length) - } else { - let tmpLeft = line.substring(0, index) - let indexLeftBracket = tmpLeft.lastIndexOf('(') - tmpLeft = tmpLeft.substring(0, indexLeftBracket) + tmpLeft.substring(indexLeftBracket + 1, tmpLeft.length) - let tmpRight = line.substring(index + macro.length, line.length) - let indexRightBracket = tmpRight.indexOf(')') - tmpRight = tmpRight.substring(0, indexRightBracket) + tmpRight.substring(indexRightBracket + 1, tmpRight.length) - line = tmpLeft + tmpRight - } - } - }) - } - processedContent += line + '\n'; - }); - - // 完成读取操作 - rl.on('close', () => { - writeFile(tempFilePath, processedContent) - }); -} - -// 读取头文件并提取所有的#define宏 -function extractMacros(headerFilePath) { - return new Promise((resolve, reject) => { - fs.readFile(headerFilePath, 'utf8', (err, data) => { - if (err) { - return reject(err); - } - - // 匹配#define指令的正则表达式 - const macroRegex = /^\s*#define\s+(\w+)/gm; - // const macroRegex = /^\s*#define\s+(\w+)(?:\s+([^\s]+))?.*$/gm; - let match; - const macros = []; - - // 使用正则表达式迭代所有匹配项 - while ((match = macroRegex.exec(data)) !== null) { - // match[1]是宏的名称,match[2]是宏的定义(如果存在) - macros.push(match[1]); - } - - resolve(macros); - }); - }); -} - -function sleep(ms) { - return new Promise(resolve => setTimeout(resolve, ms)); -} - -async function doGenerate(hFilePath, testFilePath, tsFilePath, cppFilePath) { - // 预处理文件,读出文件中所有的宏,存在数组中 - let macros = await extractMacros(hFilePath) - // 将使用宏的地方置空 - let random = generateRandomInteger(MIN_RANDOM, MAX_RANDOM) - let tempFileName = '../temp_' + random + '.h' - let tempFilePath = path.join(hFilePath, tempFileName) - removeMarco(hFilePath, tempFilePath, macros) - while (!fs.existsSync(tempFilePath)) { - await sleep(20); // 延迟 20 毫秒 - } - - let parseResult = parseFileAll(tempFilePath) - - let rootInfo = { - "namespaces": [], - "classes": [], - "functions": [], - "needCallback": false, - "typedefs": [], - } - - analyzeNameSpace(rootInfo, parseResult) - analyzeRootTypeDef(rootInfo, parseResult) - analyzeRootFunction(rootInfo, parseResult) - analyzeClasses(rootInfo, parseResult) - - // 读取Json文件 - let funcJsonPath = path.join(__dirname, '../json/function.json'); - let funcJson = getJsonCfg(funcJsonPath); - - // 读取dts文件模板 - let dtsDeclarePath = path.join(__dirname, funcJson.directFunction.dtsTemplete); - let dtsDeclare = readFile(dtsDeclarePath) - - let hFileName = hFilePath.substring(hFilePath.lastIndexOf("\\") + 1, hFilePath.length); - // 生成dts声明文件内容 - let tsContent = genTsContent(rootInfo, dtsDeclare) - tsContent = replaceAll(tsContent, "[file_introduce_replace]", hFileName) - appendWriteFile(tsFilePath, '\n' + tsContent) - - // 生成native侧文件 - generateCppFile(cppFilePath, hFilePath, funcJson, rootInfo, parseResult); - - // 生成测试用例 - generateAbilityTest(funcJson, rootInfo, parseResult, testFilePath, hFileName); - - // 删除生成的中间文件 - clearTmpFile(tempFilePath) - - console.info('Generate success') -} - -function checkPathType(path) { - try { - const stats = fs.statSync(path); - if (stats.isDirectory()) { - return "directory" - } else if (stats.isFile()) { - return "file" - } else { - return "badpath" - } - } catch (err) { - console.error(err); - } -} - -function checkFileIsNull(filePath) { - if (fs.existsSync(filePath)) { - try { - const fileContent = fs.readFileSync(filePath, 'utf-8'); - if (fileContent.trim() === '') { - return true; - } - return false; - } catch (err) { - console.error(`读取文件 ${filePath} 失败: ${err}`); - } - } - return false; -} - -function genTestTemplete(filePath, content) { - try { - fs.writeFileSync(filePath, content); - } catch (err) { - console.error(`创建文件 ${filePath} 失败: ${err}`); - } -} - - -function generateAbilityTest(funcJson, rootInfo, parseResult, testFilePath, hFileName) { - let index = hFileName.indexOf('.h') - let hFileNameReplace = hFileName.substring(0, index) - // 第一次生成时应生成框架 - let abilityTestFirstGenTempletePath = funcJson.directFunction.testTempleteDetails.abilityTestFirstGenTemplete; - let abilityTestFirstGenAbsPath = path.join(__dirname, abilityTestFirstGenTempletePath); - let abilityTestFirstGenTemplete = readFile(abilityTestFirstGenAbsPath); - abilityTestFirstGenTemplete = replaceAll(abilityTestFirstGenTemplete, '[abilitytest_name_replace]', hFileNameReplace) - - // 判断testFilePath是文件还是文件夹,若是文件夹则生成文件,同时第一次写入内容 - let realTestFilePath = testFilePath - let isDir = checkPathType(realTestFilePath) - if (isDir === 'directory') { - realTestFilePath = path.join(testFilePath, hFileNameReplace + 'Ability.test.ets'); - genTestTemplete(realTestFilePath, abilityTestFirstGenTemplete) - } else if (isDir === 'file') { - if (checkFileIsNull(realTestFilePath)) { - genTestTemplete(realTestFilePath, abilityTestFirstGenTemplete) - } - } - - // 不是第一次生成则追加写入 - let abilityTestTempletePath = funcJson.directFunction.testTempleteDetails.abilityTestTemplete; - let abilityTestTempleteAbsPath = path.join(__dirname, abilityTestTempletePath); - let abilityTestTemplete = readFile(abilityTestTempleteAbsPath); - - let genTestResult = ''; - // 生成测试用例 同时生成多个测试用例 - for (let i = 0; i < rootInfo.functions.length; i++) { - genTestResult += generateFuncTestCase(parseResult, i, rootInfo.functions[i].genName, abilityTestTemplete, hFileName); - } - const importContent = "import testNapi from 'libentry.so';"; - writeTestFile(realTestFilePath, importContent, genTestResult); -} - -function generateCppFile(cppFilePath, hFilePath, funcJson, rootInfo, parseResult) { - // 写入common.h 和 common.cpp - generateBase(cppFilePath, '', hFilePath); - - let index = hFilePath.lastIndexOf("\\"); - let indexH = hFilePath.lastIndexOf(".h"); - let napiHFileName = hFilePath.substring(index + 1, indexH).toLowerCase() + 'napi.h'; - let includes_replace = util.format('#include "%s"\n', napiHFileName); - let hFileName = hFilePath.substring(hFilePath.lastIndexOf("\\") + 1, hFilePath.length); - - let funcDeclare = ''; - let funcInit = ''; - let directFuncPath = funcJson.directFunction; - // 调用napi转换的方法 - for (let i = 0; i < rootInfo.functions.length; i++) { - let cppFileName = rootInfo.functions[i].name.toLowerCase().replace('_', '').trim(); - let thisFuncCppFilePath = path.join(cppFilePath, cppFileName + '.cpp'); - let genResult = generateDirectFunction(parseResult, i, rootInfo.functions[i].genName, directFuncPath, hFileName); - funcDeclare += genResult[0]; - funcInit += genResult[1]; - let funcBody = includes_replace + genResult[2]; - writeFile(thisFuncCppFilePath, funcBody); - } - - // init函数内容 - let cppInitTempletePath = funcJson.directFunction.initTempleteDetails.cppInitTemplete; - const cppInitTempleteAbsPath = path.join(__dirname, cppInitTempletePath); - let cppInitTemplete = readFile(cppInitTempleteAbsPath); - cppInitTemplete = replaceAll(cppInitTemplete, '[include_replace]', includes_replace); - cppInitTemplete = replaceAll(cppInitTemplete, '[init_replace]', funcInit); - let napiInitFileName = hFilePath.substring(index + 1, indexH).toLowerCase() + 'init.cpp'; - let initFilePath = path.join(cppFilePath, napiInitFileName); - writeFile(initFilePath, cppInitTemplete); - - // 生成的napi方法声明文件 - let cppDeclareTempletePath = funcJson.directFunction.cppTempleteDetails.funcHDeclare.funcHDeclareTemplete; - const cppDeclareTempleteAbsPath = path.join(__dirname, cppDeclareTempletePath); - let cppDeclareTempleteContent = readFile(cppDeclareTempleteAbsPath); - let napiHFileNameReplace = hFilePath.substring(index + 1, indexH).toLowerCase() + 'napi'; - cppDeclareTempleteContent = replaceAll(cppDeclareTempleteContent, '[h_file_name_replace]', napiHFileNameReplace.toUpperCase()); - cppDeclareTempleteContent = replaceAll(cppDeclareTempleteContent, '[func_declare_replace]', funcDeclare); - cppDeclareTempleteContent = replaceAll(cppDeclareTempleteContent, '[h_filename_replace]', - hFilePath.substring(index + 1, indexH).toLowerCase()); - let declareFilePath = path.join(cppFilePath, napiHFileName); - writeFile(declareFilePath, cppDeclareTempleteContent); -} - -function writeTestFile(filePath, importContent, funcTestContent) { - // 读取原本文件内容 - const fileContent = fs.readFileSync(filePath, 'utf8'); - const importPosition = fileContent.indexOf('import '); - let newFileContent = fileContent; - // 判断是否有该import语句,没有则添加 - if (fileContent.indexOf(importContent) < 0) { - const newImportStatement = importContent + '\n'; - newFileContent = fileContent.slice(0, importPosition) + newImportStatement + fileContent.slice(importPosition); - } - // 追加写入测试用例 - let testCasePosition = newFileContent.lastIndexOf('})') - newFileContent = newFileContent.slice(0, testCasePosition) + funcTestContent + newFileContent.slice(testCasePosition); - - writeFile(filePath, newFileContent) -} - -function replaceAll(s, sfrom, sto) { - while (s.indexOf(sfrom) >= 0) { - s = s.replace(sfrom, sto) - } - return s; -} - -function clearTmpFile(filePath) { - try { - fs.unlinkSync(filePath); - } catch (err) { - console.error(err); - } -} - -module.exports = { - doGenerate -} -- Gitee From a402ba79dee052b01a4658633f2c3664bbb4bd85 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:52:08 +0800 Subject: [PATCH 45/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/f?= =?UTF-8?q?igures/DevEco=5FDownload=5Fexe.png=20=E5=88=A0=E9=99=A4examples?= =?UTF-8?q?/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../tool/figures/DevEco_Download_exe.png | Bin 8093 -> 0 bytes 1 file changed, 0 insertions(+), 0 deletions(-) delete mode 100644 examples/napitutorials/tool/figures/DevEco_Download_exe.png diff --git a/examples/napitutorials/tool/figures/DevEco_Download_exe.png b/examples/napitutorials/tool/figures/DevEco_Download_exe.png deleted file mode 100644 index 98f8749ddd330b23611d295acdbc2feeeafec247..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 8093 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 G Date: Mon, 8 Jul 2024 16:53:23 +0800 Subject: [PATCH 46/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/f?= =?UTF-8?q?igures/DevEco=5FSign=5Fconfigs.png=20=E5=88=A0=E9=99=A4examples?= =?UTF-8?q?/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../tool/figures/DevEco_Sign_configs.png | Bin 33004 -> 0 bytes 1 file changed, 0 insertions(+), 0 deletions(-) delete mode 100644 examples/napitutorials/tool/figures/DevEco_Sign_configs.png diff --git a/examples/napitutorials/tool/figures/DevEco_Sign_configs.png b/examples/napitutorials/tool/figures/DevEco_Sign_configs.png deleted file mode 100644 index 42d44193a53b69c4a6682ccdae49f1a68c7e84ac..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 33004 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 S56pqup#yHel3;#~`-_ Date: Mon, 8 Jul 2024 16:53:40 +0800 Subject: [PATCH 47/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/f?= =?UTF-8?q?igures/DevEco=5Fadd=5Fabilitytest.png=20=E5=88=A0=E9=99=A4examp?= =?UTF-8?q?les/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../tool/figures/DevEco_add_abilitytest.png | Bin 15678 -> 0 bytes 1 file changed, 0 insertions(+), 0 deletions(-) delete mode 100644 examples/napitutorials/tool/figures/DevEco_add_abilitytest.png diff --git a/examples/napitutorials/tool/figures/DevEco_add_abilitytest.png b/examples/napitutorials/tool/figures/DevEco_add_abilitytest.png deleted file mode 100644 index de378dd5fd8c9a8f61c5861a761bdb765d318e2b..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 15678 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 Date: Mon, 8 Jul 2024 16:54:56 +0800 Subject: [PATCH 48/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/f?= =?UTF-8?q?igures/DevEco=5Fadd=5FbuildOption.png=20=E5=88=A0=E9=99=A4examp?= =?UTF-8?q?les/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0?= =?UTF-8?q?=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../tool/figures/DevEco_add_buildOption.png | Bin 25103 -> 0 bytes 1 file changed, 0 insertions(+), 0 deletions(-) delete mode 100644 examples/napitutorials/tool/figures/DevEco_add_buildOption.png diff --git a/examples/napitutorials/tool/figures/DevEco_add_buildOption.png b/examples/napitutorials/tool/figures/DevEco_add_buildOption.png deleted file mode 100644 index e8aa2279ae3fef5ea42576e55b6aae08add944df..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 25103 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 -- Gitee From fa3ecc1599c7b1f0448cbf3547baec11a88629f4 Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:55:41 +0800 Subject: [PATCH 49/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/f?= =?UTF-8?q?igures/DevEco=5Fadd=5FbusinessTest=5Fcase.png=20=E5=88=A0?= =?UTF-8?q?=E9=99=A4examples/napitutorials/tool/=EF=BC=9B=E5=A2=9E?= =?UTF-8?q?=E5=8A=A0=E5=87=A0=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../figures/DevEco_add_businessTest_case.png | Bin 86090 -> 0 bytes 1 file changed, 0 insertions(+), 0 deletions(-) delete mode 100644 examples/napitutorials/tool/figures/DevEco_add_businessTest_case.png diff --git a/examples/napitutorials/tool/figures/DevEco_add_businessTest_case.png b/examples/napitutorials/tool/figures/DevEco_add_businessTest_case.png deleted file mode 100644 index bae62d226ca61b05fdbadf66f3b0fbde25d812b6..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 86090 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

J@-c#Baf_COOpcwKR%Ue9(^aKnhtV}cf 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 -- Gitee From 683acf224ad10d7c24198de11b9967c70e10866b Mon Sep 17 00:00:00 2001 From: huruitao Date: Mon, 8 Jul 2024 16:56:29 +0800 Subject: [PATCH 50/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/f?= =?UTF-8?q?igures/DevEco=5Fadd=5FhFile.png=20=E5=88=A0=E9=99=A4examples/na?= =?UTF-8?q?pitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0=E5=87=A0=E4=B8=AAj?= =?UTF-8?q?s=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../tool/figures/DevEco_add_hFile.png | Bin 10447 -> 0 bytes 1 file changed, 0 insertions(+), 0 deletions(-) delete mode 100644 examples/napitutorials/tool/figures/DevEco_add_hFile.png diff --git a/examples/napitutorials/tool/figures/DevEco_add_hFile.png b/examples/napitutorials/tool/figures/DevEco_add_hFile.png deleted file mode 100644 index c5f1cc0e7fbaeaa82d32d78fbc68334cc1b3c520..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 10447 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 Date: Mon, 8 Jul 2024 16:57:21 +0800 Subject: [PATCH 51/91] =?UTF-8?q?"modifile=20examples/napitutorials/tool/f?= =?UTF-8?q?igures/DevEco=5Fadd=5Fthirdparty=5Flib.png=20=E5=88=A0=E9=99=A4?= =?UTF-8?q?examples/napitutorials/tool/=EF=BC=9B=E5=A2=9E=E5=8A=A0?= =?UTF-8?q?=E5=87=A0=E4=B8=AAjs=20html=E4=B8=AD=E7=9A=84;"?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: huruitao --- .../tool/figures/DevEco_add_thirdparty_lib.png | Bin 34181 -> 0 bytes 1 file changed, 0 insertions(+), 0 deletions(-) delete mode 100644 examples/napitutorials/tool/figures/DevEco_add_thirdparty_lib.png diff --git a/examples/napitutorials/tool/figures/DevEco_add_thirdparty_lib.png b/examples/napitutorials/tool/figures/DevEco_add_thirdparty_lib.png deleted file mode 100644 index 6af17a700aa15f7803c5927bcd182936781d4a72..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 34181 zcmc$`cQ~9~+y5(fM2!-nghBL(7STquJ9-zr6GZR5lc+(AAbN`)J%VAB5d=YWqs-`{ zo6+lF_PFo+d7tNff5&g{-yi$f`wy;Tt|`a0);h1XzUSxst}FJHh9U_O9T5%=4vDgo zoHh>5U3(myJ2C`+V9yZGIZ$E`cf7O}WpHYS0bAG?xOOkqU*h1@B@$m*-ow5obXPL+ z!oeZ!zWuw?=l10d4o(!EvfN8ue{&Vzhk@A+ymKB0%5nly?RcD#q~#zRr@ zpc^ucT7b}F8>0TG!KJ{^q~(uk)ZFRMbutq@xh62j9eoe2yCMlGIn*+qS$27^L@vGm z*NaH5V#3Y`|GX1PsG~#~&iePqu%9peSQ>UIj%^Okp9D9t)ACO>qN1Y0?%tkomvzU* z9^QU@47}}=Kb6Pg9c^yVq;VQZRzpr(Z!LZybMbSl~0m8wM6aoh*aD zbPBXxZuB$-T12{Y(U=6`DfagED&SXcQL}b@j&|dP_lpg2#-Nl_5%C8%bU`=tl3-59=SnUhPr?_Bu{V=1CqIUp|IZl}SaU5=ETr zcRqmf77n^FAbB+76AD>;gs%Geamj~cjRT|kQ?rjfJo?3a+GTkIl4Qh4K<(*#CzGX4 z1hL$xX76&!&Ij0^%_d?6jz1ZFE+O&!`HSZ~9~mbzXfM`qei#Y^U%XhiZs4`x%#oys zu(tFaD!J+GGmb>;<=ko(XCH+I4y*F>zK4K0d#na5|kgssmPH>b$+nMEB?s#lRMm(pubJJPZ6> z0)DgB*$GuWk>~O*A&A-@R7|iEr=ZXo6@X`yixu39`?y)CdK@2l#m@GkX~Ec$JWY@U z)P15SED0;m%8+q#($i}~o00R4na)qix6UrY-YCZ>qxVQa$BC=N)v^riu~zt9@EU9^ z{HYG?Oj>5KeqMn#K3ui7vU=`>&OTbTVwr<*l8w5? z+$W`U*-#zKpCNesX_b6T@)gKU)s~)G>Y^gnala4CgQ+jmWrLN^l+;_o?lA*FB5Ss= zQ+?a@CgY=eZoD6U%vUOfwo9Ia@|5$T$40{Q5eY`)r>i8Otn(FBSq2))NE>>T@9hNR z*hOE#;cRQ&#Qu)4wQ*K`zNFyFS;OT^3$Fz&sQ7;B@yWwF36$0J>r}0pM<)Ib%^YTd zRZ0Yo^Xv^|$~Nr@v&LO(4WqyfuVl59S#nx{$^d2FA=w&r?x1F=D01$6@nl*CiNduFHyTnxfpK2-rVPQ5z zB*3JLsiZW3$EMg%Px9!Bo{wz0@k+z}f=WdV@HeU(`>$#nA>b9OJb@{X*jx-b>n}b$q`|Z}ISU zoqa_!+#?XFT#Mw@EbX)5D5^=sE*1oFKOXviF#SfmVn6pGfqeM*3%=qqOEj}nCYOMS ze!dY*c<$*!ntVdw*CORVn+ZR-Yblkn8~M}r6RtTP>6ONKjF2pq={QzwU z`e~epf_^C(-dM?S4=?f*PsaZD7taHErkFSTm(=(v1$I<)CJE@1-3O-^6Hd3hNfSLe z$6lvEwl++ZXK{*i(^uX*Q(d-*)vU)uN{b%b*oRS60PA>hW3Pa~O;E=SEUP=l`*TT* zS5Zl|n^N!e{2eoP7dOGUhPh7W=6YCJoVq4b}}%vD)<4TwQcPhb&` z$9}xg0~0kBY_;oV*KYjybzp;y6G6IYMMd#A2|HY_#D8BTSZ=S4J=p3xJU0fr>wl1!#6^MsD;@o`u zA98^LSMl~d0bw}n?J*Mfb|J;VkqKWSxIHqz{6A0|GJL;1OsLhh?J@Ws%_k%A(i