puerts / backend-nodejs

build libnode for iOS, Android, Macos, Windows, Linux
MIT License
70 stars 23 forks source link

support for node c++ addons #13

Closed ppchavan001 closed 1 month ago

ppchavan001 commented 3 months ago

Does this Node.js backend support packages that use C++ addons, such as koffi? I am encountering errors at statements like require('koffi.node') in Unreal engine 5.2

If support is not currently available, are there any plans to include it in the future, or are there any workarounds to use these packages?

chexiongsheng commented 2 months ago

You need to recompile the Node.js C++ addons for your program, similar to how Node.js C++ addons require an electron-rebuild process to be used in Electron.

ppchavan001 commented 2 months ago

I don't have my own node C++ addons. I am trying to use a npm package (koffi) that uses C++ addons to function properly.

When I run the following script using system node (v16.16.0) its shows a message box. But when I call this script from Unreal engine (puerts with node backend) I get unhandledRejection,TypeError: koffi.load is not a function,TypeError

I am guessing its because puerts is unable to load koffi.node file from node_modules\koffi\build\koffi\win32_x64 since DefaultJSModuleLoader only returns files with .js, .mjs, etc. Other js only node_modules installed in the same location are working properly so I don't think its an issue related to path.

npm install koffi

import *  as koffi from 'koffi';

// Load the shared library
const lib = koffi.load('user32.dll');

// Declare constants
const MB_YESNO = 0x4;
const MB_ICONQUESTION = 0x20;
const MB_ICONINFORMATION = 0x40;
const IDYES = 6;

// Find functions
const MessageBoxA = lib.func('__stdcall', 'MessageBoxA', 'int', ['void *', 'str', 'str', 'uint']);
const MessageBoxW = lib.func('__stdcall', 'MessageBoxW', 'int', ['void *', 'str16', 'str16', 'uint']);

let ret = MessageBoxA(null, 'Do you want another message box?', 'Koffi', MB_YESNO | MB_ICONQUESTION);
if (ret == IDYES)
    MessageBoxW(null, 'Hello World!', 'Koffi', MB_ICONINFORMATION);

koffi package doc

chexiongsheng commented 2 months ago

It is possible that your error is caused by the DefaultJSModuleLoader not looking for the koffi.node file. However, even if it finds the file, it will still fail to load because Node.js C++ addons include a reference to node.exe. At least on Windows, if the executable is not named node.exe, it will fail to load. For example, in the case of Electron, electron-rebuild recompiles and links to the Electron executable. However, currently, Puerts does not have similar support.

ppchavan001 commented 1 month ago

I got it working for Win64 using MinHook.

I have tested the following Node modules in UE 5.2 on Windows without rebuilding any modules from source:

You can review the changes in this commit.

If you have no further questions, you can close this issue.

chexiongsheng commented 1 month ago

This is a good attempt, but it's a bit hacker, I would rather provide a tool similar to electron-rebuild.