在 node.js 绑定中实现继承

Jay*_*esh 5 c++ v8 prototypal-inheritance node.js

我正在围绕 C++ 库编写 Node.js 绑定。我可以识别 C++ 库中的关键对象,我可以将它们作为类公开给 Node.js(即 ObjectWrap 的衍生物)。我还可以看到这些对象之间的继承关系。

我怎样才能暴露ClassAClassBClassC如Node.js的类(的衍生物ObjectWrap),并操纵他们的原型(在V8中的C ++代码),以便ClassBClassC是衍生物ClassA

Jay*_*esh 4

v8::FunctionTemplate这可以使用的方法来完成Inherit这里解释一下。这是一个工作示例。

C++代码:

#include <v8.h>
#include <node.h>

using namespace node;
using namespace v8;

class BaseClass : ObjectWrap
{
public:
  static Persistent<FunctionTemplate> s_ct;
  static void Init(v8::Handle<Object> target)
  {
    Local<FunctionTemplate> t = FunctionTemplate::New(New);

    s_ct = Persistent<FunctionTemplate>::New(t);
    s_ct->InstanceTemplate()->SetInternalFieldCount(1);
    s_ct->SetClassName(String::NewSymbol("BaseClass"));

    NODE_SET_PROTOTYPE_METHOD(s_ct, "getName", getName);

    target->Set(String::NewSymbol("BaseClass"), s_ct->GetFunction());
  }

  BaseClass(){}    
  ~BaseClass(){}

  static v8::Handle<Value> New(const Arguments& args)
  {
    HandleScope scope;
    return args.This();
  }

  static v8::Handle<Value> getName(const Arguments& args)
  {
    HandleScope scope;
    return scope.Close(String::New("Base"));
  }
};

Persistent<FunctionTemplate> BaseClass::s_ct;

class DerivedClass : ObjectWrap
{
public:
  static Persistent<FunctionTemplate> s_ct;
  static void Init(v8::Handle<Object> target)
  {
    Local<FunctionTemplate> t = FunctionTemplate::New(New);

    s_ct = Persistent<FunctionTemplate>::New(t);

    // XXX Inherit from BaseClass
    s_ct->Inherit(BaseClass::s_ct); 

    s_ct->InstanceTemplate()->SetInternalFieldCount(1);
    s_ct->SetClassName(String::NewSymbol("DerivedClass"));

    NODE_SET_PROTOTYPE_METHOD(s_ct, "getAge", getAge);

    target->Set(String::NewSymbol("DerivedClass"), s_ct->GetFunction());
  }

  DerivedClass() {}
  ~DerivedClass() {}

  static v8::Handle<Value> New(const Arguments& args) {
    HandleScope scope;
    return args.This();
  }

  static v8::Handle<Value> getAge(const Arguments& args)
  {
    HandleScope scope;
    return scope.Close(Number::New(42));
  }
};

Persistent<FunctionTemplate> DerivedClass::s_ct;

extern "C" {
  static void init (v8::Handle<Object> target)
  {
    BaseClass::Init(target);
    DerivedClass::Init(target);
  }

  NODE_MODULE(mymodule, init);
}
Run Code Online (Sandbox Code Playgroud)

将其置于标准node-gyp配置中,您可以使用以下 javascript 对其进行测试

var mymodule = require('./build/Release/mymodule');
var baseObject = new mymodule.BaseClass();
var dervObject = new mymodule.DerivedClass();

console.log(baseObject.getName());
console.log(dervObject.getName(), dervObject.getAge());
Run Code Online (Sandbox Code Playgroud)