wsモジュール
wsモジュールは、WebSocketプロトコル(RFC-6455に準拠する)の実装ライブラリです。
socket.ioのように多機能ではありませんが、シンプルな作りで非常に高速に動作するのが特徴です。
※socket.ioも内部でwsを使用しています
環境構築方法
今回使用した動作環境は以下のとおりです。
- OS : MacOS X 10.7.4
- Node.js : v0.8.15
- npm : 1.1.66
適当なディレクトリを作成し、そこでnpmを使用して必要モジュールをインストールします。
今回はexpressも使用するので、いっしょにインストールしましょう。
1 2 3 | % mkdir ws % cd ws % npm install ws express |
wsモジュールを使ったチャット- server:nodejs & client:html
ありふれた例ですが、wsモジュールとexpressモジュールを使用してシンプルなチャットをつくってみましょう。
まずはサーバ側のモジュールをapp.jsという名前で作成します。
1 2 3 4 5 6 7 8 9 | //app.js var WebSocketServer = require('ws').Server , http = require('http') , express = require('express') , app = express(); app.use(express.static(__dirname + '/')); var server = http.createServer(app); var wss = new WebSocketServer({server:server}); | cs |
expressモジュールからHttpサーバを作成し、wsモジュールのServerの引数にしてWebSocket用サーバオブジェクトを作成します。
WebSocketの接続を保存しておく変数、connectionsを用意しておきます。
WebSocketServerのonメソッドを使用し、接続時、切断時、メッセージ受信時の処理を記述します。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 | var connections = []; wss.on('connection', function (ws,req) { //wss.on('connection'...)은 웹소켓을 연결하는 ws와 클라이언트 쪽의 데이터를 담고 있는 req를 콜백으로 반환한다. connections.push(ws); ws.on('close', function () { connections = connections.filter(function (conn, i) { return (conn === ws) ? false : true; }); }); ws.on('message', function (message) { console.log('message:', message); broadcast(JSON.stringify(message)); }); }); | cs |
なお、接続時にはconnections変数へ接続オブジェクトを保存し、切断時にはconnections変数から削除します。
broadcastはこの後定義する関数です。
wsモジュールには、Websocketで接続しているユーザー全員にブロードキャストする機能はありません。
接続時に保存している配列を精査して全員にsendメソッドでメッセージを送ります。
1 2 3 4 5 6 7 8 | function broadcast(message) { connections.forEach(function (con, i) { con.send(message); }); }; server.listen(3000); | cs |
最後に3000番ポートでサーバを起動しています。
app.js全文です。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 | //app.js var WebSocketServer = require('ws').Server , http = require('http') , express = require('express') , app = express(); app.use(express.static(__dirname + '/')); var server = http.createServer(app); var wss = new WebSocketServer({server:server}); //Websocket接続を保存しておく var connections = []; //接続時 wss.on('connection', function (ws) { //配列にWebSocket接続を保存 connections.push(ws); //切断時 ws.on('close', function () { connections = connections.filter(function (conn, i) { return (conn === ws) ? false : true; }); }); //メッセージ送信時 ws.on('message', function (message) { console.log('message:', message); broadcast(JSON.stringify(message)); }); }); //ブロードキャストを行う function broadcast(message) { connections.forEach(function (con, i) { con.send(message); }); }; server.listen(3000); | cs |
次はindex.htmlファイルです。
sendボタンを押すと、テキストフィールドの文字をブロードキャストします。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 | <!DOCTYPE html> <html> <head> <script> function send() { ws.send(document.getElementById('msg').value); } var host = window.document.location.host.replace(/:.*/, ''); var ws = new WebSocket('ws://' + host + ':3000'); ws.onmessage = function (event) { document.getElementById("messages").innerHTML += "<div>" + JSON.parse(event.data) + "</div>"; console.log(JSON.parse(event.data)); }; </script> </head> <body> <strong>ws chat</strong><br> <input type="text" id="msg"/> <input type="button" value="send" onclick="send()"/> <br> <hr> <div id="messages"/> </body> </html> | cs |
サーバを起動し、ブラウザでhttp://localhost:3000/index.htmlを複数ブラウザで開いた後、文字を送信してみてください。
チャットができてますね。
1 | % node app.js |
5分で動かせるWebsocket
https://qiita.com/okumurakengo/items/a8ccea065f5659d1a1de
wsモジュールを使ったチャット- server:nodejs & client:nodejs
server-side.js
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 | let WebSocketServer = require('ws').Server , http = require('http') , express = require('express') , app = express(); let server = http.createServer(app); let wss = new WebSocketServer({server:server}); wss.on('connection', function(ws) { // When connection is success console.dir('connection on'); console.log('Data sending from server to client started'); _sendDataTimeGap(ws); // Processing data from client socket ws.on('message', function(message) { console.log(' message from client : ', message); }); ws.on('error',function(error){ console.log('error from client : ',error); }); ws.on('close',function(code,reason){ console.log('close from client : ',`code:${code}`,` reason:${reason}`); }); // ws.close(); }); server.listen(3000); /** * Function * @params {filePath:string} path of uploaded image file * @params {langs:array} array of langs from front */ function _sendDataTimeGap(ws){ setTimeout(function() { ws.send('Server said Hello, Client' + new Date()); }, 2000); } | cs |
client-side
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 | const fs = require('fs'); const WebSocket = require('ws'); var ws = new WebSocket('ws://localhost:3000'); // When connection is success ws.on('open', function() { console.log('socket connected'); console.log('Data sending from client to server started'); _sendDataTimeGap(ws); }); // Processing data from server socket ws.on('close', function close(e) { console.log('close from server : ',e); }); ws.on('message', function message(e) { console.log('message from server : ', e); }); ws.on('error', function error(e) { console.log('error from server :',e); }); /** * Function * @params {filePath:string} path of uploaded image file * @params {langs:array} array of langs from front */ function _sendDataTimeGap(ws){ setTimeout(function() { ws.send('Client said Hello, Server' + new Date()); }, 2000); } | cs |
https://www.npmjs.com/package/ws
まとめ
node.jsでWebSocketを使いたい場合、ほとんどのケースでsocket.ioを使用しているのではないでしょうか。
しかし、socket.ioほどの機能は必要なかったり(ブロードキャスト機能もありませんが・・・)、
wsをベースにしてライブラリを作成する場合には直接使用することもあるかもしれません。
参考サイトなど
- Github: https://github.com/einaros/ws/
'C Lang > JS Technic' 카테고리의 다른 글
array.shift() (0) | 2018.08.15 |
---|---|
nodejs의 웹소켓연결을 위한 모듈3 websocket:서버쪽 nodejs, 클라이언트쪽 nodejs & html (0) | 2018.08.15 |
Node.js의 Events와 EventEmitter (0) | 2018.08.13 |
?를 이용해 한 줄로 쓰는 if문 (0) | 2018.08.09 |
Node.js StreamAPI★ (0) | 2018.08.08 |