2013-04-13 32 views
9

Tôi đang viết các liên kết node.js và tôi muốn tạo chuỗi JSON từ v8 :: Các cá thể đối tượng. Tôi muốn làm điều đó trong C++. Vì node.js đã có JSON.stringify, tôi muốn sử dụng nó. Nhưng tôi không biết cách truy cập nó từ mã C++.Truy cập JSON.stringify từ các liên kết C++ node.js

Trả lời

5

Bạn cần lấy một tham chiếu đến đối tượng chung, sau đó lấy phương thức xâu chuỗi;

Local<Object> obj = ... // Thing to stringify 

// Get the global object. 
// Same as using 'global' in Node 
Local<Object> global = Context::GetCurrent()->Global(); 

// Get JSON 
// Same as using 'global.JSON' 
Local<Object> JSON = Local<Object>::Cast(
    global->Get(String::New("JSON"))); 

// Get stringify 
// Same as using 'global.JSON.stringify' 
Local<Function> stringify = Local<Function>::Cast(
    JSON->Get(String::New("stringify"))); 

// Stringify the object 
// Same as using 'global.JSON.stringify.apply(global.JSON, [ obj ]) 
Local<Value> args[] = { obj }; 
Local<String> result = Local<String>::Cast(stringify->Call(JSON, 1, args)); 
+0

Một số thứ dường như đã thay đổi trong V8 API: 1. Không có 'GetCurrent' và thường bạn lấy toàn cục từ phân lập bằng cách sử dụng' isolate-> GetCurrentContext() -> Global() '. 2. Không có 'String :: New()' và thường bạn muốn 'String :: NewFromUTF8()'. Đừng nghĩ rằng điều này biện minh cho một câu trả lời khác nhưng nó sẽ được gọi nếu bạn cập nhật của bạn. – Stav

1

Một số API nút đã thay đổi từ việc xuất bản OP. Giả sử một phiên bản node.js 7.7.1, mã biến đổi thành một cái gì đó dọc theo các dòng;

std::string ToJson(v8::Local<v8::Value> obj) 
{ 
    if (obj.IsEmpty()) 
     return std::string(); 

    v8::Isolate* isolate = v8::Isolate::GetCurrent(); 
    v8::HandleScope scope(isolate); 

    v8::Local<v8::Object> JSON = isolate->GetCurrentContext()-> 
     Global()->Get(v8::String::NewFromUtf8(isolate, "JSON"))->ToObject(); 
    v8::Local<v8::Function> stringify = JSON->Get(
     v8::String::NewFromUtf8(isolate, "stringify")).As<v8::Function>(); 

    v8::Local<v8::Value> args[] = { obj }; 
    // to "pretty print" use the arguments below instead... 
    //v8::Local<v8::Value> args[] = { obj, v8::Null(isolate), v8::Integer::New(isolate, 2) }; 

    v8::Local<v8::Value> const result = stringify->Call(JSON, 
     std::size(args), args); 
    v8::String::Utf8Value const json(result); 

    return std::string(*json); 
} 

Về cơ bản, các mã được đối tượng JSON từ động cơ, có được một tham chiếu đến các chức năng stringify của đối tượng đó, và sau đó gọi nó. Mã này tương đương với javascript;

var j = JSON.stringify(obj); 

Các lựa chọn thay thế khác dựa trên v8 bao gồm sử dụng lớp JSON.

auto str = v8::JSON::Stringify(v8::Isolate::GetCurrent()->GetCurrentContext(), obj).ToLocalChecked(); 
v8::String::Utf8Value json{ str }; 
return std::string(*json); 
Các vấn đề liên quan