5

I am trying to create a basic native node addon where a javascript array is passed from node and then processed in c++. The problem is I cannot figure out how to correctly pass the array. I can instantiate the array without issue but assigning it using info[0].as throws errors.

My c++ code is

#include <napi.h>

using namespace Napi;
using namespace std;

Value Add(const CallbackInfo& info) 
{
  Env env = info.Env();


  Array result = Napi::Array::New(env);
  Array a = info[0].As<Array>;

  double arg1 = info[1].As<Number>().DoubleValue();
  Number num = Napi::Number::New(env, 2 + arg1);

  return num;
}

The error I am getting is

../cppsrc/main.cpp: In function ‘Napi::Value Add(const Napi::CallbackInfo&)’:
../cppsrc/main.cpp:12:21: error: conversion from ‘<unresolved overloaded function type>’ to non-scalar type ‘Napi::Array’ requested
   Array a = info[0].As<Array>;
             ~~~~~~~~^~~~~~~~~

What is the correct way to pass an array to c++? Is it even possible?

4 Answers 4

6

This works for me:

void runSetPropertyAsyncWorker(const CallbackInfo& info) 
{
    std::string path = info[0].As<Napi::String>();
    int property = info[1].As<Number>();
    int dataSize = info[2].As<Number>();
    Array b = info[3].As<Array>();
    for(int i = 0; i<b.Length(); i++)
    {
      Napi::Value v = b[i];
      if (v.IsNumber())
      {
        int value = (int)v.As<Napi::Number>();
        ...
        ...
      }
    }

    ...
    ...

    Function callback = info[4].As<Function>();
    AsyncWorker* asyncWorker = new SetPropertyAsyncWorker(callback, ...);
    asyncWorker->Queue();
}
Sign up to request clarification or add additional context in comments.

Comments

3

Use Napi::Object. Napi::Array is actually inherited from Napi::Object.

You could replace the code Array a = info[0].As<Array>; with Array a = info[0].ToObject();.

You can then access the data members via Value operator[] (uint32_t index) const

Source: https://nodejs.github.io/node-addon-api/class_napi_1_1_object.html

Edit: Bonus feature, if an argument that is not an object is passed, this will automatically trigger an Error: Object Expected.

Comments

1

error code here:

Array a = info[0].As<Array>;

which should be

Array a = info[0].As<Array>();

Comments

0

I was not able to find a solution to the actual question of interacting with the Javascript object directly with node-addon-api. The Solution that I chose to go with is JSON.stringify any arrays or objects and then parse then in c++ is a library called rapid json. This proves to be the only way to interface with javascript objects that i've been able to find

2 Comments

That is not true. Plus, it slows down the code dramatically because you will have to parse the JSON in c++. It is also not very convenient in JavaScript.
I understand it was not an ideal solution but it was the best i could come up with at the time. With the size of the data that I was working with it was not really a speed concern. Also rapid JSON is a very fast c++ json library.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.