如何通过 meson 构建系统编译 Node.js 原生 api 扩展

问题描述 投票:0回答:1

我想编译

Node.js
C/C++ 扩展而不使用
node-gyp
包。

我有使用

meson
的经验,并会用它来编译
Node.js
模块。

你可以建议如何编译

Node.js
本机模块的示例吗?

P.S.我使用了一些带有静态专有库的

subproject
,并且
node-gyp
对于这个硬构建来说是非常简单的实用程序。

node.js linux node-modules meson-build
1个回答
2
投票

我同意这是一个好主意,因为

node-gyp
会生成 Makefile,而 Meson 使用现代 Ninja 工作速度更快。另外,使用
node-gyp
构建会导致
node.h
发出警告,您对此无能为力,但 Meson 允许使用
is_system: true
抑制它们。

对于这个答案,我使用了这里的示例插件。 C++ 文件:

// hello.cc
#include <node.h>

namespace demo {

using v8::FunctionCallbackInfo;
using v8::Isolate;
using v8::Local;
using v8::Object;
using v8::String;
using v8::Value;

void Method(const FunctionCallbackInfo<Value>& args) {
  Isolate* isolate = args.GetIsolate();
  args.GetReturnValue().Set(String::NewFromUtf8(
      isolate, "world").ToLocalChecked());
}

void Initialize(Local<Object> exports) {
  NODE_SET_METHOD(exports, "hello", Method);
}

NODE_MODULE(NODE_GYP_MODULE_NAME, Initialize)

}  // namespace demo

meson.build
;它将编译插件,并通过加载
node
来测试它的功能,然后从插件中调用
hello()

project('C++ node example addon', 'cpp')

inc_node = include_directories('/usr/include/node', is_system: true)

# For compatibility with node-gyp we use "shared_module" rather than
# "shared_library". The difference important in the current context is that
# shared_module will happily allow undefined references at link-time. It may or may
# not be what you want, feel free to change to `shared_library`, in which case you
# have to also link it with find_library('node')
shared_module(
  'hello',
  ['hello.cc'],
  include_directories : [inc_node],
  name_prefix: '',     # don't prepend "lib"
  name_suffix: 'node', # required for addon to load properly
)

node = find_program('node')

test('addon',
     node,
     args: ['-e',
            'const addon = require("./hello.node");'
            + 'console.log(addon.hello());'
           ]
    )

这是运行它的示例:

$ meson build
The Meson build system
Version: 0.62.2
Source dir: /tmp/node_C_hello_world
Build dir: /tmp/node_C_hello_world/build
Build type: native build
Project name: C++ node example addon
Project version: undefined
C++ compiler for the host machine: c++ (gcc 12.1.1 "c++ (GCC) 12.1.1 20220507 (Red Hat 12.1.1-1)")
C++ linker for the host machine: c++ ld.bfd 2.37-27
Host machine cpu family: x86_64
Host machine cpu: x86_64
Library node found: YES
Program node found: YES (/usr/bin/node)
Build targets in project: 1

Found ninja-1.10.2 at /usr/bin/ninja
$ ninja -C build/
ninja: Entering directory `build/'
[2/2] Linking target hello.node
$ ninja -C build/ test
ninja: Entering directory `build/'
[0/1] Running all tests.
1/1 addon        OK              0.20s


Ok:                 1
Expected Fail:      0
Fail:               0
Unexpected Pass:    0
Skipped:            0
Timeout:            0

Full log written to /tmp/node_C_hello_world/build/meson-logs/testlog.txt

一些注意事项:

  • 插件库必须有
    .node
    后缀,否则
    node
    将无法加载它并带有
    SyntaxError: Invalid or unexpected token
  • nodejs-devel
    (或者在您的系统上调用带有
    node.h
    的任何软件包)
    软件包,不幸的是,缺少 pkg-config
    .pc
    文件,因此您必须直接调用
    include_directories()
    而不是简单地使用
     dependency()
    致电。
  • node-gyp
    添加了一些奇特的参数,我不确定是否需要。我不是 Nodejs 开发人员,所以不能在这件事上说任何有用的内容,但以下是我认为对于更复杂的插件可能很重要的内容:
    • 链接参数
      -rdynamic
    • 编译参数
      -DNODE_GYP_MODULE_NAME=addon -DUSING_UV_SHARED=1 -DUSING_V8_SHARED=1 -DBUILDING_NODE_EXTENSION
© www.soinside.com 2019 - 2024. All rights reserved.