websocket の echo server を作ってみた
目的
- html5 の websocket を使って簡単な通信をしてみる
ソース
websocket.html1 <!DOCTYPE html> 2 3 <html> 4 5 <head> 6 <meta charset="utf-8"> 7 8 <script type="text/javascript"> 9 var ws = new WebSocket("ws://localhost:8080/"); 10 11 ws.onopen = function(event) { 12 alert("websocket " + event + " is opened"); 13 }; 14 15 ws.onmessage = function(event) { 16 alert(event.data); 17 }; 18 19 function send() { 20 var msg = document.getElementById("msg").value; 21 ws.send(msg); 22 } 23 24 </script> 25 </head> 26 27 <body> 28 <input type="text" id="msg" /> 29 <button onclick="send();">send</button> 30 </body> 31 32 </html>
echo_server.py
1 import socket 2 3 BUFSIZE = 4096 4 5 host = socket.gethostbyname('localhost') 6 port = 8080 7 8 sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 9 sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1) 10 sock.bind((host, port)) 11 sock.listen(1) 12 13 print 'waiting for connection...' 14 15 (client_sock, client_addr) = sock.accept() 16 msg = client_sock.recv(BUFSIZE) 17 18 [head, body] = msg.split("\r\n", 1) 19 header = {} 20 21 for line in body.splitlines(): 22 if line == "": 23 break 24 else: 25 [key, value] = line.split(": ", 1) 26 header[key] = value.strip() 27 28 # websocket handshake 29 handshake = "HTTP/1.1 101 Web Socket Protocol Handshake\r\n" 30 handshake += "Upgrade: %s\r\n" % header['Upgrade'] 31 handshake += "Connection: %s\r\n" % header['Connection'] 32 handshake += "WebSocket-Origin:%s\r\n" % header['Origin'] 33 handshake += "WebSocket-Location: ws://localhost:8080/\r\n" 34 handshake += "\r\n" 35 36 client_sock.send(handshake) 37 38 print 'connection start' 39 print '---------- ---------- ----------' 40 41 while True: 42 msg = client_sock.recv(BUFSIZE) 43 44 if msg == "": 45 break 46 else: 47 print "client: %s" % msg[0:len(msg)-1] 48 client_sock.send(msg) 49 50 client_sock.close() 51 52 sock.close() 53 54 print '---------- ---------- ----------' 55 print 'connection end' 56
実行
- chrome から文字列を送ってみる
connection start ---------- ---------- ---------- client: this client: is client: a client: test ---------- ---------- ---------- connection end
考察
- そもそも最初は通信自体がうまくいなかった
- handshake を行わないと通信を確立してくれない
- 47行目で受け取った文字列の後ろ2バイトを削っている
- 終端文字として何か入ってるみたいだが文字化けするので削った