Skip to content

Instantly share code, notes, and snippets.

@fujiwara
Created June 21, 2010 02:52
Show Gist options
  • Star 4 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save fujiwara/446327 to your computer and use it in GitHub Desktop.
Save fujiwara/446327 to your computer and use it in GitHub Desktop.
<!Docutype HTML>
<html lang="ja">
<head>
<meta charset="utf-8">
<title>UserStreamsClient</title>
<script src="http://www.google.com/jsapi"></script>
<script> google.load("jquery", "1.4") </script>
<style>
div.tweet {
border-bottom: 1px solid #999;
margin: 3px;
}
</style>
</head>
<body>
<div id="tweets"></div>
<script>
var tweets_buf = [];
var id = 0;
var generate_id = function() {
id = id + 1;
return "tweet-" + id;
};
var clear_buf = function() {
while (tweets_buf.length > 100) {
var id = tweets_buf.shift();
$("#"+id).remove();
}
};
var writer = function(input) {
try {
data = eval(input);
}
catch(error) {
console.log("JSON parse error: " + error + " input: " + input);
}
if (!data) {
console.log("got data=" + data);
return "";
}
if (data.text && data.user) {
var html = "<div>";
html += "<img src='" + data.user.profile_image_url + "' width=48 height=48 align=left> ";
html += data.user.screen_name + ": " + data.text + " (" + data.created_at + ")";
html += "<br clear=all></div>";
return html;
}
else if (data.event) {
return("<div class='event'>" + data.event + "</div>");
}
else {
return("<div class='event'>unkown event</div>");
}
}
var load_more = function() {
$.get(
"/stream",
function(data) {
if (data != "") {
var id = generate_id();
$("#tweets").prepend("<div class='tweet' style='display:none' id='" + id + "'>" + writer(data) + "</div>");
$("#"+id).slideDown(300);
tweets_buf.push(id);
clear_buf();
}
load_more();
}
);
};
load_more();
</script>
</body>
</html>
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();
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment