简体   繁体   English

如何使用可读 stream 从 NodeJS 发送数据到 C++

[英]how to send data with Readable stream from NodeJS to C++

I'm currently sending data from C++ to NodeJS passing a NodeJS readableStream.push.bind(readableStream) to the C++ binding code and writing onto the stream from C++ using I'm currently sending data from C++ to NodeJS passing a NodeJS readableStream.push.bind(readableStream) to the C++ binding code and writing onto the stream from C++ using

Napi::Function push = info[0].As<Napi::Function>();
Napi::ThreadSafeFunction push_safe = Napi::ThreadSafeFunction::New(env, push, "push", 0, 1);
push_safe.BlockingCall(data, custom_callback);

Now I want to be able to send data to the C++ binding, using a NodeJS Stream, but I can't figure out if C++ can accept a Stream, and calling a C++ version of .on('data', (data) => {}) on it, something like: Now I want to be able to send data to the C++ binding, using a NodeJS Stream, but I can't figure out if C++ can accept a Stream, and calling a C++ version of .on('data', (data) => {})就可以了,类似于:

example NodeJS:示例 NodeJS:

const read_stream = fs.createReadStream("./random.bin");
mybinding.myfunc(read_stream);

example C++:例如 C++:

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

  auto on_data_lambda = [](data)
  {
    std::cout << "new data arrived from nodejs stream: " << data << std::endl;
  }

  /*some magic*/
}


Implementing this with all the bells and whistles is not trivial.用所有的花里胡哨来实现这一点并非易事。 As always, the most complex part is handling all the errors.与往常一样,最复杂的部分是处理所有错误。

I suggest you go check in Node.js sources src/js_stream.cc which contains something similar and you will understand why a good/fast implementation is difficult.我建议你 go 检查 Node.js 源src/js_stream.cc包含类似的东西,你会明白为什么一个好的/快速的实现是困难的。

If you want to keep it simple, you can start by creating a JS reference to your C++ on_data function:如果你想保持简单,你可以首先创建一个对 C++ on_data function 的 JS 引用:

Napi::Function on_data_ref = Napi::Function::New(env, on_data_, "cpp_callback");

on_data should have a JS-callable function signature: on_data应该有一个 JS 可调用的 function 签名:

Value on_data(const CallbackInfo& info)

Then you can register this function as an event receiver:然后您可以将此 function 注册为事件接收器:

Napi::Value onValue = stream.Get("on");
if (!onValue.IsFunction())
  throw Napi::Error::New(env, "This is not an event emitter");
Napi::Function on = onValue.As<Napi::Function>();
on.Call(stream, {Napi::String::New(env, "data"), on_data_ref});

If you do this, data will start flowing.如果你这样做,数据将开始流动。 But you still have to do correctly the error handling and everything else.但是您仍然必须正确地进行错误处理和其他所有操作。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM