我需要一些帮助来解决我的问题。 基本上,我想"打电话"来自C ++插件的javascript函数,我已经搜索过它并发现了类似的内容。
这是我的.js文件
const myaddon = process.binding('myaddon');
function Foo() {
console.log("wooo");
}
myaddon.getfoo(Foo);
myaddon.callfoo(); // just to test if C++ Call js function work
这是我的.cpp
Local<Function> pfOnScriptInit;
Local<Object> globel;
void test(const FunctionCallbackInfo<Value>& args)
{
pfOnScriptInit = Local<Function>::Cast(args[0]);
}
void call(const FunctionCallbackInfo<Value>& args)
{
pfOnScriptInit->Call(globel, 0, nullptr);
}
void initAll(Local<Object> target, Local<Value> unused, Local<Context> context, void* priv)
{
node::Environment* env = node::Environment::GetCurrent(context);
globel = env->context()->Global();
env->SetMethod(target, "getfoo", test);
env->SetMethod(target, "callfoo", call);
}
NODE_MODULE_CONTEXT_AWARE_BUILTIN(fivemp, node::fivemp::initAll)
调用myaddon.callfoo();
函数时出现此错误:
TypeError:非法调用
答案 0 :(得分:3)
这个问题有点陈旧,但这是一个常见的问题,已被问到couple times。在我看来,这些答案没有正确的答案。因此,我走了!
在我回答您的问题之前,请允许我说您应该使用Native Abstractions for Node.js来编写Node.js插件。这将使您的插件可以跨Node.js版本移植。
此外,您应该查看官方插件文档here,以及带有Nan示例的repo。
那就是说,你的代码有一个很大的常见错误:你混淆地使用本地对象作为持久性。换句话说,从函数范围声明ext_tables.sql
是完全错误的。这两个不能在功能范围内声明:
Local<Function>
当然,你不能像这样分配Local<Function> pfOnScriptInit;
Local<Object> globel;
:
Local<Function>
这个本地对象将由v8的垃圾收集器回收 - 它将不再存在。因此,您需要使用pfOnScriptInit = Local<Function>::Cast(args[0]);
类型。这是一个使用Nan编写的示例,它可能会告诉您它是如何完成的:
persistent
这是JS方面:
#include <nan.h>
static Nan::CopyablePersistentTraits<v8::Function>::CopyablePersistent _cb;
static void SetCallback(const Nan::FunctionCallbackInfo<v8::Value>& info) {
_cb = Nan::Persistent<v8::Function>(info[0].As<v8::Function>());
}
static void RunCallback(const Nan::FunctionCallbackInfo<v8::Value>& info) {
Nan::MakeCallback(Nan::GetCurrentContext()->Global(), Nan::New(_cb), 0, 0);
_cb.Reset();
}
void RunThisCallback(const Nan::FunctionCallbackInfo<v8::Value>& info) {
v8::Local<v8::Function> cb = info[0].As<v8::Function>();
Nan::MakeCallback(Nan::GetCurrentContext()->Global(), cb, 0, 0);
}
static void Init(v8::Local<v8::Object> exports, v8::Local<v8::Object> module) {
Nan::SetMethod(exports, "setCallback", SetCallback);
Nan::SetMethod(exports, "call", RunCallback);
Nan::SetMethod(exports, "callThis", RunThisCallback);
}
NODE_MODULE(addon, Init)
有关v8本地vs持久性的更多信息,您应该查看v8的文档。 Scott Frees还有一本关于Node.js插件的好书,https://scottfrees.com/ebooks/nodecpp/。