我正在玩用C ++创建Node.js模块,但我对v8 :: Arguments类感到难过。假设我有一个用于发送电子邮件的Javascript类,它有一个带有此签名的方法:
Mailer::sendEmail(Array recipients, String sender, String message);
这将被称为:
mailer.sendEmail(["joe@gmail.com", "sally@gmail.com"], "fred@gmail.com", "Hi there");
现在在C ++领域,我有一个带有这个签名的类函数:
SendEmail(const v8::Arguments& args)
在Javascript中支持我的Mailer :: sendEmail方法。 SendEmail函数将创建我的Emailer类的新实例,该实例本身具有带此签名的类函数:
send(std::list<std::string> recipients, std::string from, std::string message)
这就是我失去的地方。我不知道如何从 args 获取值,并将它们转换为常规C ++类型,因此我可以将值传递给我的发送函数。据我了解,传递给Mailer :: sendEmail的3个值将在 args [0] , args [1] 和 args [2]中提供。 。我甚至理解我可以像if (!args[0]->IsArray())
那样进行类型检查,但实际上将 args [0] 转换为std::list<std::string>
是我不知道该怎么做。
编辑:我发现了这样做的一种破解方式,但我仍然认为V8有一些内置方法可以更清晰地处理这个问题。
static Handle<Value> SendEmail(const Arguments& args)
{
HandleScope scope;
list<string> values;
Local<Object> obj = args[0]->ToObject();
Local<Array> props = obj->GetPropertyNames();
// Iterate through args[0], adding each element to our list
for(unsigned int i = 0; i < props->Length(); i++) {
String::AsciiValue val(obj->Get(i)->ToString());
values.push_front(string(*val));
}
// Display the values in the list for debugging purposes
for (list<string>::iterator it = values.begin(); it != values.end(); it++) {
cout << *it << endl;
}
return scope.Close(args.This());
}
答案 0 :(得分:50)
我知道这是一个较老的主题,但我倾向于这样做的方式如下:
Handle<Value> MethodName (const Arguments& args) {
// get the param
v8::String::Utf8Value param1(args[0]->ToString());
// convert it to string
std::string foo = std::string(*param1);
}
答案 1 :(得分:6)
我可以找到转换为JS类型和C ++类型的最佳方法是使用v8-juice,它提供了类型转换方法。具体来说,我正在使用v8-convert,它是v8-juice的衍生产品,仅包含转换方法。
将args [0]转换为std :: list是一行:
std::list<std::string> values = cvv8::CastFromJS<std::list<std::string> >(args[0]);
答案 2 :(得分:6)
如果您使用的是NaN(native abstractions for node),请尝试以下代码:
std::string myString(*NanAsciiString(args[0]));