Node.js C++将多个CC文件扩展为一个模块
node.js c++ extension multiple cc files into one module
我正在玩Node.js来评估如何与Node.js连接基于复杂C的库。这个库对数据库执行几个操作,nodejs 应该调用这个函数并通过 rest API 返回结果。
在玩节点.js方面的例子时,我遇到了一个问题:
我正在尝试基于两个 cc 文件构建一个插件:
插件1.c:
#define BUILDING_NODE_EXTENSION
#include <node.h>
using namespace v8;
Handle<Value> Add(const Arguments& args) {
HandleScope scope;
if (args.Length() < 2) {
ThrowException(Exception::TypeError(String::New("Wrong number of arguments")));
return scope.Close(Undefined());
}
if (!args[0]->IsNumber() || !args[1]->IsNumber()) {
ThrowException(Exception::TypeError(String::New("Wrong arguments")));
return scope.Close(Undefined());
}
Local<Number> num = Number::New(args[0]->NumberValue() +
args[1]->NumberValue());
return scope.Close(num);
}
void Init(Handle<Object> exports) {
exports->Set(String::NewSymbol("add"),
FunctionTemplate::New(Add)->GetFunction());
}
NODE_MODULE(addon, Init)
插件2.c:
#define BUILDING_NODE_EXTENSION
#include <node.h>
using namespace v8;
Handle<Value> Del(const Arguments& args) {
HandleScope scope2;
if (args.Length() < 2) {
ThrowException(Exception::TypeError(String::New("Wrong number of arguments")));
return scope2.Close(Undefined());
}
if (!args[0]->IsNumber() || !args[1]->IsNumber()) {
ThrowException(Exception::TypeError(String::New("Wrong arguments")));
return scope2.Close(Undefined());
}
Local<Number> num = Number::New(args[0]->NumberValue() -
args[1]->NumberValue());
return scope2.Close(num);
}
void Init(Handle<Object> exports) {
exports->Set(String::NewSymbol("del"),
FunctionTemplate::New(Del)->GetFunction());
}
NODE_MODULE(addon, Init)
还有我的绑定.gyp:
{
"targets": [
{
"target_name": "addon",
"sources": ["addon1.cc", "addon2.cc"]
}
]
}
调用 node.gyp 配置构建以以下错误消息结束:
CXX(target) Release/obj.target/addon/addon2.o
SOLINK_MODULE(target) Release/addon.node
duplicate symbol __Z4InitN2v86HandleINS_6ObjectEEE in:
Release/obj.target/addon/addon1.o
Release/obj.target/addon/addon2.o
ld: 1 duplicate symbol for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation)
make: *** [Release/addon.node] Error 1
gyp ERR! build error
gyp ERR! stack Error: `make` failed with exit code: 2
gyp ERR! stack at ChildProcess.onExit (/opt/local/lib/node_modules/node-gyp/lib/build.js:267:23)
gyp ERR! stack at ChildProcess.EventEmitter.emit (events.js:98:17)
gyp ERR! stack at Process.ChildProcess._handle.onexit (child_process.js:797:12)
gyp ERR! System Darwin 13.1.0
gyp ERR! command "node" "/opt/local/bin/node-gyp" "configure" "build"
gyp ERR! cwd /Applications/MAMP/htdocs/nodejs/test2
gyp ERR! node -v v0.10.26
gyp ERR! node-gyp -v v0.13.0
gyp ERR! not ok
我希望你们中的任何人都有如何解决这个问题的提示。
提前谢谢。
问题很明显:在两个翻译单元(源文件)中都有一个名为 Init
的函数。在构建单个模块时,应该只有一个Init
函数。
解决此问题的简单方法是删除一个Init
函数,并在剩余的Init
函数中"注册"add
和del
名称。
解决方案:在一个源文件中,您拥有唯一的Init
函数,并声明缺少的Add
或Del
函数(即您制作函数原型):
// Declare function prototypes
Handle<Value> Add(const Arguments& args);
Handle<Value> Del(const Arguments& args);
// The one and only initialization function
void Init(Handle<Object> exports) {
exports->Set(String::NewSymbol("add"),
FunctionTemplate::New(Add)->GetFunction());
exports->Set(String::NewSymbol("del"),
FunctionTemplate::New(Del)->GetFunction());
}
NODE_MODULE(addon, Init)
实际上,您现在可以将其作为单独的源文件。
从您的实现中,我可以看到您正在尝试实现两个不同的模块 add 和 del。
node.js 提供了不同类型的插件模式,如 http://nodejs.org/api/addons.html 所建议
的那样在我看来,您尝试实现的内容可以通过包装C++对象来获得
相关文章:
- 如果C++对象的类在另一个boost模块中声明,如何使用boost将指向该对象的指针返回到python
- 处理程序的模块列表中有一个错误的模块"WebSocketModule"
- 是否可以使用另一个lua文件中定义的表,该表在当前文件中不需要作为模块
- 导出从另一个模块导入的类
- 为Qt项目的每个模块添加一个包含
- 如何在OMNET++中收到来自前一个模块的所有消息后将一条消息发送到下一个模块
- 我应该把Boost.Python的.so文件放在哪里,这样我就可以把它作为一个模块导入,以及我如何将它与Python 2
- 在C++中嵌入Python:在Python脚本中导入模块在一个函数调用过程中有效,但在另一个调用过程中无效
- 创建一个生成文件来构建切换的模块
- 在另一个应用程序中嵌入python时,如何在子模块(即scipy.optimize.nnls)中导入或调用函数
- 在C++中,"static initialization fiasco"是否仅影响对另一个模块中定义的对象的数据成员的引用?
- 在N2073提案的情况下以及作为一个整体的c++模块设计
- 在一个共享对象中提升 python 多个模块
- .exe vs .dll 作为一个程序的模块
- C++ 结构函数体调用另一个结构函数,同一个模块
- SWIG:从另一个模块返回对象的函数
- 如何在c++ OCX模块中指定一个接受void*参数的函数
- Android.如何检查一个模块是否已经存在
- 模板被另一个模块使用时是如何工作的
- 如何有效地为一个有很多依赖的c++产品使用git存储库/子模块