Created
July 28, 2014 21:38
-
-
Save hiroosak/1be1ade683f22dcb4e1d to your computer and use it in GitHub Desktop.
node-gypを使ってnative addonを作成する (2) - 非同期関数をとりあえず作ってみる ref: http://qiita.com/taizo/items/44bf02878f5fc0842703
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#include <node.h> | |
#include <v8.h> | |
using namespace v8; | |
typedef struct asyncData { | |
Persistent<Function> callback; | |
const char *result; | |
} AsyncData; | |
void AsyncWork(uv_work_t *req) { | |
AsyncData *asyncData = (AsyncData *)req->data; | |
asyncData->result = "Hello World!"; | |
} | |
void AsyncAfter(uv_work_t *req) { | |
HandleScope scope; | |
AsyncData *asyncData = (AsyncData *)req->data; | |
Handle<Value> argv[] = { | |
Null(), | |
String::New(asyncData->result) | |
}; | |
// surround in a try/catch for safety | |
TryCatch try_catch; | |
// execute the callback function | |
asyncData->callback->Call(Context::GetCurrent()->Global(), 2, argv); | |
if (try_catch.HasCaught()) { | |
node::FatalException(try_catch); | |
} | |
delete asyncData; | |
delete req; | |
} | |
Handle<Value> Async(const Arguments& args) { | |
HandleScope scope; | |
if (args.Length() < 1) { | |
ThrowException(Exception::TypeError(String::New("1 arguments expected"))); | |
return scope.Close(Undefined()); | |
} | |
if (!args[0]->IsFunction()) { | |
ThrowException(Exception::TypeError(String::New("Wrong arguments"))); | |
return scope.Close(Undefined()); | |
} | |
Local<Function> callback = Local<Function>::Cast(args[0]); | |
uv_loop_t *loop = uv_default_loop(); | |
uv_work_t *req = new uv_work_t; | |
AsyncData *asyncData = new AsyncData; | |
asyncData->callback = Persistent<Function>::New(callback); | |
req->data = asyncData; | |
uv_queue_work( | |
loop, | |
req, | |
AsyncWork, | |
(uv_after_work_cb)AsyncAfter | |
); | |
return scope.Close(Undefined()); | |
} | |
void init(Handle<Object> exports) { | |
exports->Set(String::NewSymbol("async"), | |
FunctionTemplate::New(Async)->GetFunction()); | |
} | |
NODE_MODULE(addon, init) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
var addon = require('./build/Release/addon'); | |
addon.async(function(err, res) { | |
console.log('err', err); // null | |
console.log('res', res); // Hello World | |
}); | |
addon.async(3); // TypeError: Wrong arguments |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
{ | |
"targets": [{ | |
"target_name": "addon", | |
"sources": [ | |
"async.cc" | |
] | |
}] | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
uv_loop_t *loop = uv_default_loop(); | |
uv_work_t *req = new uv_work_t; | |
AsyncData *asyncData = new AsyncData; | |
asyncData->callback = Persistent<Function>::New(callback); | |
req->data = asyncData; // 引き回すデータを入れる | |
uv_queue_work( | |
loop, | |
req, | |
AsyncWork, // 実際の処理 | |
(uv_after_work_cb)AsyncAfter // 実行後の処理 | |
); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment