Skip to content

Instantly share code, notes, and snippets.

@katahirado
Created June 5, 2012 16:34
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save katahirado/2876111 to your computer and use it in GitHub Desktop.
Save katahirado/2876111 to your computer and use it in GitHub Desktop.
Sqale EventMachine test
require 'sinatra'
get '/' do
'Hello World'
end
<html>
<head>
<script src='js/swfobject.js'></script>
<script src='js/FABridge.js'></script>
<script src='js/web_socket.js'></script>
<script>
var Socket = "MozWebSocket" in window ? MozWebSocket : WebSocket;
var ws;
function reciveDataSpace(string) {
var element = document.getElementById("reciveDataSpace");
var p = document.createElement("p");
p.appendChild(document.createTextNode(string));
element.appendChild(p);
}
function loginState(string) {
var element = document.getElementById("loginState");
element.innerHTML = "<p>" + string + "</p>";
}
function init() {
Socket = "MozWebSocket" in window ? MozWebSocket : WebSocket;
ws = new Socket("ws://localhost:8080/");
ws.onmessage = function(evt) {
if("[CreateLoginUserCmd_OK]" == evt.data){
loginState("login");
changeloginState();
}
else if("[CreateLoginUserCmd_NG]" == evt.data){
loginState("The login name is already used. ");
}
else{
reciveDataSpace("Message: " + evt.data);
}
};
ws.onclose = function() { reciveDataSpace("socket closed"); };
ws.onopen = function() {
reciveDataSpace("connected...");
}
}
function sendMessage(){
var sendMsg = document.getElementById("message");
var name = document.getElementById("loginName");
if(sendMsg.value == "") return;
if(name.value == "") return;
ws.send("[" + name.value + "]:" + sendMsg.value);
sendMsg.value = "";
}
function sendLogin(){
loginState("");
var name = document.getElementById("loginName");
if(name.value == "") {
loginState("Name is empty.");
return;
}
ws.send("[CreateLoginUserCmd]:" + name.value);
}
function changeloginState(){
var name = document.getElementById("loginName");
if(name.value == "") return;
var login = document.getElementById("buttonLogin");
login.disabled = true;
var name = document.getElementById("loginName");
name.disabled = true;
var sendBtn = document.getElementById("buttonSend");
sendBtn.disabled = false;
};
</script>
</head>
<body onload="init();">
<div>
ログイン名:
<INPUT TYPE="text" id="loginName" size="20" value="">
<INPUT TYPE="button" id="buttonLogin" VALUE="ログイン" onClick="sendLogin()">
</div>
<div id="loginState"><p></p></div>
<div>
送信メッセージ:
<INPUT TYPE="text" id="message" size="20" value="">
<INPUT TYPE="button" id="buttonSend" VALUE="送信" disabled="true" onClick="sendMessage()">
</div>
<div>
受信データ
<div id="reciveDataSpace"></div>
</div>
</body>
</html>
require './app'
run Sinatra::Application
#Gemfile
gem "sinatra"
gem "em-websocket"
#Gemfile.lock
GEM
specs:
addressable (2.2.8)
em-websocket (0.3.6)
addressable (>= 2.1.1)
eventmachine (>= 0.12.9)
eventmachine (0.12.10)
rack (1.4.1)
rack-protection (1.2.0)
rack
sinatra (1.3.2)
rack (‾> 1.3, >= 1.3.6)
rack-protection (‾> 1.2)
tilt (‾> 1.3, >= 1.3.3)
tilt (1.3.3)
PLATFORMS
ruby
DEPENDENCIES
em-websocket
sinatra
#/usr/bin/env ruby
require 'rubygems'
require 'em-websocket'
# チャット用モジュール ユーザー管理を追加
module ChatModule
# ログイン要求コマンド
CMD_LOGIN = "[CreateLoginUserCmd]"
CMD_RETURN_LOGIN_OK = "[CreateLoginUserCmd_OK]"
CMD_RETURN_LOGIN_NG = "[CreateLoginUserCmd_NG]"
# ユーザー管理
@@connected_clients = Hash.new
# 受信したメッセージがログイン要求かどうか
def loginMessage?(msg)
msgArray = msg.strip.split(":")
1 < msgArray.size && msgArray[0].include?(CMD_LOGIN)
end
# 接続ユーザー全員にメッセージを送る
def sendBroadcast(msg)
return if msg.empty?
@@connected_clients.each_value { |c| c.send(msg) }
puts msg
end
# ログイン処理
def login(msg)
msgArray = msg.strip.split(":")
name = msgArray[1][0...(msgArray[1].size-1)]
if @@connected_clients.has_key?(name) == false
@loginName = name
@@connected_clients[@loginName] = self
send(CMD_RETURN_LOGIN_OK)
puts "Login name is #{@loginName}"
else
send(CMD_RETURN_LOGIN_NG)
end
end
#ログアウト処理
def logout()
if @loginName && @loginName.empty? == false
msg = "[#{@loginName}] is logout."
puts msg
@@connected_clients.delete(@loginName)
@@connected_clients.each_value { |c| c.send(msg) }
end
puts "WebSocket closed"
end
end
EM::WebSocket.start(:host => "0.0.0.0", :port => 8080) { |ws|
ws.extend(ChatModule)
ws.onopen{
ws.send("Welcome! Please login!")
}
ws.onmessage { |msg|
return if msg.strip.size < 1
if ws.loginMessage?(msg)
ws.login(msg)
else
ws.sendBroadcast(msg)
end
}
ws.onclose{
ws.logout
}
ws.onerror{ |e|
ws.logout
puts "Error: #{e.message}"
}
}
@katahirado
Copy link
Author

WebSocket.rbとchat.htmlは下記のコードそのままです。

https://github.com/icchi/WebSocketChat

chat.htmlはpublic/ディレクトリを用意して、その下に配置しています。

@katahirado
Copy link
Author

やったこと。
Sinatraでのデプロイ確認。
Sinatraのpublicに静的ファイル置いてchat.htmlが表示されるのを確認。
sshでログインして、bundle exec ruby Websocket.rb
/home/sqale/current/vendor/bundle/ruby/1.9.1/gems/eventmachine-0.12.10/lib/eventmachine.rb:572:in start_tcp_server': no acceptor (RuntimeError) from /home/sqale/current/vendor/bundle/ruby/1.9.1/gems/eventmachine-0.12.10/lib/eventmachine.rb:572:instart_server'
from /home/sqale/current/vendor/bundle/ruby/1.9.1/gems/em-websocket-0.3.6/lib/em-websocket/websocket.rb:14:in block in start' from /home/sqale/current/vendor/bundle/ruby/1.9.1/gems/eventmachine-0.12.10/lib/eventmachine.rb:256:incall'
from /home/sqale/current/vendor/bundle/ruby/1.9.1/gems/eventmachine-0.12.10/lib/eventmachine.rb:256:in run_machine' from /home/sqale/current/vendor/bundle/ruby/1.9.1/gems/eventmachine-0.12.10/lib/eventmachine.rb:256:inrun'
from /home/sqale/current/vendor/bundle/ruby/1.9.1/gems/em-websocket-0.3.6/lib/em-websocket/websocket.rb:9:in start' from WebSocketChat.rb:54:in

'

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment