2011
Sep
23

這篇文章只適用於 Node.js version 0.10.x,如果你是使用 0.11 與 0.12 以上的版本,請忽略本文。

Node.js像php一樣可以寫extension,不過在Node.js裡叫做addon,同樣是使用C or C++,在php中我們是透過Zend function來製作 extension ,而在Node.js,是透過 Google v8 引擎來製作。

  • 第一步我們得先設定 python library的路徑,我是設定成: PYTHONPATH=/usr/local/lib/python2.7
  • 第二步是寫好你的c code
  • 第三步寫一個wscript ,就如同makefile一樣,指定要編譯的檔案名稱
  • 第四步執行編譯 sudo node-waf configure build ,執行後會自動建立build dir
  • 最後,寫個 Node.js , require addon 來用吧

Node.js Addon 寫法實作

現在我們就先寫一個簡單的 c code 來測試吧,首先我們要載入相關的header file,最基本的兩個header是 v8 與 node ,include 後,順便先呼叫 namespace,以方便後續使用

hello.cc
  1. #include "v8.h"
  2. #include "node.h"
  3. using namespace v8;
  4. using namespace node;

接著實做 init ,require Node.js addon 後,最先執行的function,這裡我用v8 String物件,宣告一個字串hello,及一個字串world,並指定hello=world,再用兩種不同的方式,定義function, 範例 「hello.cc 」

hello.cc
  1. extern "C" void init (Handle<Object> target){
  2. HandleScope scope;
  3. target->Set(String::New("hello"), String::New("world"));
  4. target->Set(String::New("func"),FunctionTemplate::New(func)->GetFunction());
  5. NODE_SET_METHOD(target, "func2", func2);
  6. }

實做 func與func2,這兩個function,我這先簡單寫一點東西,測試一下囉

hello.cc
  1. static Handle<Value> func(const Arguments& args){
  2. return String::New("the return value");
  3. }
  4. static Handle<Value> func2(const Arguments& args){
  5. return True();
  6. }

編譯 Node.js Addon

編譯出來的 addon 副檔名一定要是 .node ,否則執行會有問題。

make
  1. mode=compile g++ -Wall -O3 -fPIC -Dposix -DDSO_EXT=so -DREUSE_CONTEXT -shared -DHAVE_CONFIG_H -g -O2 -I/usr/local/include/node -c hello.cc -o hello.o
  2. g++ -shared -lpthread -lv8 -lrt -ldl -o hello.node hello.o

執行與測試 Node.js

寫個js 載入 hello 並印出物件,範例「hello」

Example
  1. var s=require('./hello.node');
  2. console.log(s);
  3. console.log(s.func());
  4. console.log(s.func2())

結果輸出:

Example
  1. [puritys]addon$ node hello.js
  2. { hello: 'world', func: [Function], func2: [Function] }
  3. the return value
  4. true

Node.js Addon 範例下載


目前回應 Comments(1 comments)

  • Sam 2014/03/14

    感謝版大分享, 可是為什麼compile出來要有.node?我看國外他們compile出來沒有加.node也可以, 這是版本問題嗎?

    Reply

    Admin

    每個檔案,習慣上都會給一個副檔名,所以我固定都會用 .node,如果副檔名是別的,例如 .so , .o 這樣 Node.js addon 會無法載入;若是你不給副檔名,也是可以正確載入的。

回應 (Leave a comment)