Используя NAN, как я могу вызвать Javascript из функции C++, которая не является NAN_METHOD?

Я делаю родную надстройку C++ с использованием NAN. Мой файл AddOn.cc содержит метод NAN Update(), который вызывается из Javascript. Затем Update() вызывает библиотеку зависимостей C++, которая, в свою очередь, вызывает мою функцию NON-NAN в Addon.cc StatusHandler(). Это в свою очередь вызывает обратный вызов Javascript.

Перед вызовом Update() код Javascript вызывает Startup () и передает функцию для использования в качестве обратного вызова из StatusHandler().

Вот соответствующий код из моего файла ADDON.CC:

// Javascript status delegate
v8::Local<v8::Function> jsStatusDelegate;

NAN_METHOD(Startup) {
    // Set Javascript status delegate
    jsStatusDelegate = v8::Local<v8::Function>::Cast(info[0]);
}

// Update method called from Javascript
NAN_METHOD(Update) {
    // Call method that will call back to StatusHandler
    myLibrary->Update();
}

// Status delegate called back from dependency library
void StatusHandler(LibStatus &status) {
    // Create callback parameters
    const int argc = 1;
    v8::Local<v8::Value> args[argc];
    args[0] = Nan::New("All Good.").ToLocalChecked();

    TRACE("=========== Calling Javascript Delegate");
    Nan::Callback callbackFunc(jsStatusDelegate);
    v8::Local<v8::Value> jsReturnValue = callbackFunc.Call(argc, args);
}

Вот соответствующий код из моего тестового скрипта:

var addon = require('bindings')('addon');

addon.Startup(StatusDelegate);
addon.Update();

function StatusDelegate(status) {
    console.log("******** Javascript StatusDelegate ********");
    console.log(status);
}

Все компилируется и работает без ошибок с обеих сторон. Я вижу TRACE из оператора C++, но не вижу распечатки из StatusDelegate().

Что я сделал неправильно? StatusDelegate () действительно вызывается? Если так, почему я не вижу записи в журнале?

1 ответ

Решение

Вот соответствующие изменения, которые сделали это работать.

// Javascript status delegate
Nan::Callback jsStatusDelegate;

NAN_METHOD(Startup) {
    // Set Javascript status delegate
    jsStatusDelegate.Reset(info[0].As<v8::Function>());
}

// Status delegate called back from dependency library
void StatusHandler(LibStatus &status) {
    // ...same code...
    TRACE("=========== Calling Javascript Delegate");

    // New code
    v8::Local<v8::Value> jsReturnValue = jsStatusDelegate.Call(argc, args);
}

Это тонкое изменение, и я не совсем уверен, почему этот способ работает, а другой нет. Казалось бы, "Nan::Callback" каким-то образом сохраняется, а "v8::Local" - нет.

Другие вопросы по тегам