|
var sys = require('sys'), |
|
http = require('http'), |
|
fs = require('fs'), |
|
auth = "************************", // "ユーザ名:パスワード" を Base64 したもの |
|
queue = new process.EventEmitter(), // イベント通知用 |
|
backlog = [], |
|
maxlogs = 100, |
|
port = 5000; |
|
|
|
|
|
var main = function() { |
|
http.createServer(handle_request).listen(port); |
|
|
|
var client = http.createClient(80, "chirpstream.twitter.com"); |
|
var request = client.request( |
|
'GET', '/2b/user.json', |
|
{ 'Host': 'chirpstream.twitter.com', |
|
'Authorization': auth } // とりあえず Basic 認証 |
|
); |
|
request.addListener('response', function (response) { |
|
sys.puts('STATUS: ' + response.statusCode); |
|
sys.puts('HEADERS: ' + JSON.stringify(response.headers)); |
|
response.setEncoding('utf8'); |
|
response.addListener('data', read_chunked(queue_writer)); |
|
}); |
|
request.end(); |
|
}; |
|
|
|
var queue_writer = function(input) { |
|
if (queue.listeners("message").length) { // listener がいたらイベント通知 |
|
queue.emit("message", input); |
|
} |
|
else { // いなければ backlog に積んでおく |
|
while ( backlog.length > maxlogs ) { |
|
backlog.shift(); |
|
} |
|
backlog.push(input); |
|
} |
|
}; |
|
|
|
// バッファリングして改行ごとに writer に渡す |
|
var read_chunked = function( writer ) { |
|
var buf = ""; |
|
return function(chunk) { |
|
if (chunk.match(/\n/)) { |
|
var chunks = chunk.split(/\r?\n/); |
|
writer( buf + chunks.shift() ); |
|
if (chunks.length) { |
|
buf = chunks.pop(); |
|
} |
|
var c = "" |
|
while ( c = chunks.shift() ) { |
|
writer(c); |
|
} |
|
return; |
|
} |
|
buf += chunk; |
|
} |
|
}; |
|
|
|
// HTTP server のリクエストハンドラ |
|
var handle_request = function (request, response) { |
|
if (request.url == "/") { |
|
// ファイルを読み込んで返す |
|
response.writeHead(200, {'Content-Type': 'text/html; charset=utf-8'}); |
|
var file = fs.createReadStream("./client.html"); |
|
file.addListener('data', function(data) { response.write(data) }); |
|
file.addListener('end', function(chunk) { response.end() }); |
|
} |
|
else if (request.url == "/stream") { |
|
var send_response = function(msg) { |
|
response.writeHead(200, {'Content-Type': 'application/json'}); |
|
response.end(msg); |
|
}; |
|
if (backlog.length) { // backlogがたまってたらそれを返す |
|
send_response(backlog.shift()); |
|
} |
|
else { |
|
// イベント通知を待つ listener を作って callback で返す |
|
var listener = function(msg) { |
|
send_response(msg); |
|
queue.removeListener("message", listener); |
|
}; |
|
queue.addListener("message", listener); |
|
} |
|
} |
|
else { |
|
response.writeHead(404, {'Content-Type': 'text/plain'}); |
|
response.end("Not Found\n"); |
|
} |
|
}; |
|
|
|
main(); |