-->

2011-11-30

node.jsのtest

var
http = require("http"),
querystring = require("querystring"),
convertDate = function(date){
  return ("0" + date.getHours()).slice(-2) + ":" +
    ("0" + date.getMinutes()).slice(-2) + ":" +
    ("0" + date.getSeconds()).slice(-2);
},
htmlEscape = (function(){
  var pattern = /([&<>\"])/g,
  escapeChars = {"&":"&amp;", "<":"&lt;", ">":"&gt;", "\"":"&quot;"},
  urlPattern = /(^|[^-_.!~*\'()a-zA-Z0-9;\/?:@&=+$,%#])(https?:\/\/[-_.!~*\'()a-zA-Z0-9;\/?:@&=+$,%#]{5,63})($|[^-_.!~*\'()a-zA-Z0-9;\/?:@&=+$,%#])/;
  return function(str){
    return String(str).replace(pattern, function(){
      return escapeChars[arguments[1]];
    }).replace(urlPattern, "$1<a href=\"$2\">$2</a>$3");
  };
})(),
appUrl = "http://192.168.0.100/nodejs/",
readCount = 0,
writeCount = 0,
bbsLog = [];
http.createServer(function (request, response) {
  var
  postMessage = function(){
    var body = "";
    request.on("data", function(data){
      body += data;
    });
    request.on("end", function(){
      var $_POST =  querystring.parse(body), writeDate;
      if (typeof $_POST["message"] == "string" && $_POST["message"] !== "")
      {
        writeDate = new Date;
        bbsLog.unshift({"date":writeDate, "message":$_POST["message"]});
        while (bbsLog.length > 10)
        {
          bbsLog.pop();
        }
        writeCount++;
        console.log(writeDate, "postMessage", readCount, writeCount, $_POST);
      }
      response.writeHead(302, {"Location": appUrl});
      response.end();
    });
  },
  getMessage = function(){
    var
    bbsLogToHtml = function(){
      var i, buf = "";
      for (i = 0; i < bbsLog.length; i++)
      {
        buf += convertDate(bbsLog[i].date);
        buf += " : ";
        buf += htmlEscape(bbsLog[i].message);
        buf += "<br/>";
      }
      return buf;
    };
    readCount++;
    response.writeHead(200, {"Content-Type": "text/html; charset=UTF-8"});
    response.end(
      "<html>" +
        "<head>" +
        "<style>" +
        "*{" +
        "font-family: monospace, sans-serif;" +
        "}" +
        "</style>" +
        "</head>" +
        "<body>" +
        "<h1>Sample BBS</h1>" +
        "readCount : " + readCount + "<br/>" +
        "writeCount : " + writeCount + "<br/>" +
        "<form action=\"" + appUrl + "\" method=\"post\">" +
        "<input type=\"text\" name=\"message\" value=\"Hello World\" size=\"63\"/>" +
        "<input type=\"submit\"/>" +
        "&nbsp;<a href=\"" + appUrl + "\">Reload</a>" +
        "</form>" +
        bbsLogToHtml() +
        "</body></html>");
    console.log(new Date, "getMessage", readCount, writeCount);
  };
  if (request.method == "POST")
  {
    postMessage();
  }
  else
  {
    getMessage();
  }
}).listen(8124);
console.log("Server running at http://127.0.0.1:8124/");

node.jsのマニュアルの最初の方にあるサンプル+postデータの取得のサンプルです。
普通は express, ejs などのフレームワークやテンプレートエンジンを使うらしいのでそっちが良いです。
ab2でベンチマーク(getMessage()を連続で実行)を取った所-c5000~10000ぐらいまでは性能が低下せずに-c20000では処理量が半分まで落ちた。
サンプルの処理内容は単純だがメモリの利用量が少ないことやシングルタスク(Phenom(tm) 9350e)でRequests per secondが2500前後になることを見ると、実用性があるように思う。
エラーが不親切な気もするが設定があるのかもしれない。
// インストール(gentooの場合)
$ sudo ACCEPT_KEYWORDS="~*" emerge --oneshot -avt =net-libs/nodejs-0.6.2
// 実行
$ node example.js > /tmp/nodejs.example.js.log 2>&1 &
// テスト
$ ab2 -n1000 -c100 http://127.0.0.1:8124/ 2>&1|grep "^Requests per second"
Requests per second:    2621.41 [#/sec] (mean)

参考URL。
http://nodejs.jp/nodejs.org_ja/api/synopsis.html
http://onlineconsultant.jp/pukiwiki/?node.js%20GET%20POST%E3%83%91%E3%83%A9%E3%83%A1%E3%83%BC%E3%82%BF%E3%83%BC%E3%82%92%E5%8F%96%E5%BE%97%E3%81%99%E3%82%8B
http://snippets.dzone.com/posts/show/13311

0 件のコメント: