一から勉強させてください( ̄ω ̄;)

最下級エンジニアが日々の学びをアウトプットしていくだけのブログです。

Node.js導入してみた

今回は時代に取り残されないために話題のNode.jsを導入して、ちょっと使ってみたときのことを書きたいと思います。

まず導入する前に「そもそもNode.jsとは何なのか」というところですが、僕はとりあえず「サーバーサイドJavaScriptっしょ?」ぐらいの情報しか知りませんでしたのでちょっと調べてみました。


参考にさせて頂いた記事↓
http://gihyo.jp/dev/serial/01/nodejs/0001
http://www.atmarkit.co.jp/fwcr/rensai2/nodejs02/02.html


Node.jsとは,ブラウザGoogle Chrome用に開発されたJavaScriptエンジンV8がサーバ上でプログラムを実行できるように,ファイルやネットワークI/Oなど多くの機能を追加したもの


ふむ。


Node.jsでは“軽量で効率良く”というのを実現するために次の2つのモデルを採用しています。

・ノンブロッキングI/O
・イベントループ


ふむ。


ここで、ちょっと自分なりにこの「ノンブロッキングI/O」、「イベントループ」について考察しました。ちょっと長いですが、ご勘弁を。


まずイベントループの対になるモデルが「スレッドモデル」。
このモデルでは、アクセス毎にスレッドを生成して処理を行うため、アクセス数が多くなるとスレッド生成のために大量のメモリを消費してしまう問題があります。

これに対して、一つのスレッドで処理を順番に行い続けるモデルが「イベントループモデル」。
このモデルではアクセス数が増えてもスレッドをむやみに増殖させたりはしないので、メモリの消費を抑える事ができると。

でもこのイベントループモデル、くっそ重い処理がやってきてしまった場合、やはりシングルスレッド故にパフォーマンスが大幅に低下するリスクもあります。

上の記事でも書かれていますが、例えば「データベースにアクセスして検索を実行して結果を取得する」といった処理がきた場合、その結果が返ってくるまで次の処理に移れない(ブロッキングI/O)つまり待機状態になっちゃいます。

一つのスレッドで処理してるんだからこれはきつい!!(lll ̄ロ ̄)ノノ))│・ロ・│

そこで登場するのが「ノンブロッキングI/Oモデル」
これは結果が返ってくるまで待機するのではなく、「データベース内検索しといてー」って依頼を出した後、結果を待たずにもう次の処理に移る、つまり処理を非同期で行うモデルです。
これは結果の受け取りをコールバックで実現するので、スムーズに処理する事が可能になります。


以上が自分なりに考えたイベントループとノンブロッキングI/Oです。間違ってたら誰かHELP!!!


ちなみにおもしろい例えをされているこんな記事も発見しました↓

http://satoshun00.hatenadiary.com/entry/2012/08/02/172936


自分もちょっと真似して「お昼のコンビニ」で例えてみます。

お昼のコンビニでは、


・レジ
・お弁当温める


の二つの処理を同時に大量に捌く必要があるとします。
これを上記で書いた各モデルで考えてみると、


スレッドモデル→
レジ2カ所に店員さんが一人ずつ立って処理するモデル。一人当たりの負荷は小さいが人件費が2倍。
まあ普通のコンビニの風景ですな。


イベントループ→
レジ1カ所に店員さんが一人で立って処理するモデル。一人当たりの負荷ハンパないが人件費は一人分で済む。ちゃんと捌ききればスレッドモデルより利益が出る。


ブロッキングI/O→
レジでお弁当を温めたいというお客さんがいた場合、そのお弁当が温まるまでレンジの前でじっと待機してる、駄目店員モデル。次のお客さんはレジの前でじっと待たされている状態。これはひどいw


ノンブロッキングI/O→
レジでお弁当を温めたいというお客さんがいた場合、レンジにお弁当をセットして、次のお客さんの会計のためレジに戻る、優秀な店員モデル。
「チーン」ってレンジが鳴ったら前のお客さんにお弁当を渡して、またレジに戻る、、みたいな。


つまりNode.jsは
優秀な店員さんが一人で仕事を回しているコンビニみたいなものか…
って違いますかね。。


前置きが長くなりました。。

ではベタですが早速、Node.jsの導入〜Hello Worldまでの流れをざっと書きます(笑)


まず、http://nodejs.org/download/にアクセスして、nodeをインストール。
(自分はMac版を入れました。)
               ↓
インストールしたら、勝手に$PATHにnodeのインストール先が登録されるみたい。
これでもう使えるようになったぽいです!楽っ!
               ↓
早速、hello_world.jsというjsファイルを用意してHello Worldを出力する命令を書いてみました。
hello_world.jsのコードは、

//HTTPサーバー、クライアントを使用するにはrequire("http")が必ず必要
var http = require("http");

//新しいwebサーバーオブジェクトを返す
var server = http.createServer();

//onはnode.jsのイベント登録メソッド
server.on("request", function(req, res){
	res.writeHead(200, {"Content-Type": "text/plain"});
	res.end("Hello World\n");
});

//指定されたport, Hostのコネクション受け入れを開始
server.listen(8888, "localhost");

//ログ
console.log("Server running at http://127.0.0.1:8888");


こんな感じで8888番ポートにHTTPアクセスがあった場合、Hello Worldを出力するプログラムを書いてみました。
今回は、細かい説明はコメントアウトに書いてサボっちゃいました。。すんません。

あとはhello_world.jsが置いてあるディレクトリにターミナルで移動して、

node hello_world.js

とするだけ。
これで127.0.0.1:8888(localhost:8888)にアクセスしたら、ちゃんとHello Worldを確認できました。

ターミナルでCtrl + Cを2回押さない限り、ずっとこの状態を維持できるみたいですね。


以上、前置きが大半を占めましたが、Node.jsの導入が完了しました。

次回はwebsocketとかフレームワークも勉強して、Node.jsでアプリをつくることにチャレンジしたいと思います。
がんばろー

小さな事からコツコツと。