Table of Contents
WebSocket による双方向リアルタイム通信を行えるPHPライブラリ「Ratchet」をXAMPPのローカルサーバーに設定し、実際に通信のチュートリアルを実行する手順についてです。
公式ページ(Ratchet – Tutorial: Your first app)のチュートリアルドキュメントと違う操作が必要だった部分があったので、それについても記載します。
インストールのためにComposerを準備
Ratchet のインストールにはPHPライブラリ依存を管理するツールである「Composer」を利用するのが現実的です。Ratchet は複数のライブラリを使用しているため、一つひとつ手動でそれらを用意するのは大変だからです。
まず Composer のダウンロードページにアクセスします。
そのページに記載されているインストール用コマンドをターミナルにコピー&ペーストしてください。コマンドは以下のような形式ですが、変更される可能性があるので公式ページからコピーしてください。
実際にターミナルに入力すると、以下のように出力され、インストールが完了します。
インストールするディレクトリは任意ですが、今回はホームディレクトリ(~/)にインストールしています。以下のように composer.phar が追加されていることを確認してください。
以上で Composer の準備は完了です。
Ratchetをインストール
XAMPP の htdocs ディレクトリに任意の名前のフォルダを作成し、ターミナルでアクセスできる状態にします。この例では MyChat というフォルダ名にしています。
その後、ターミナルで次のコマンドを入力します。
php ~/composer.phar require cboden/ratchet
すると、ターミナルには以下のように出力されます。
フォルダ内に以下のファイルが作成されます。
通信のための設定とスクリプトの作成
造られたファイルの中の composer.json を開き autoload の5行を追記します。require の部分は既に記述されているはずです。
{ "autoload": { "psr-4": { "MyApp\\": "src" } }, "require": { "cboden/ratchet": "^0.4.3" } }
そして、ディレクトリ MyChat にフォルダ src/ を作成し、以下のPHPスクリプト(Chat.php)を作成します。
Chat.php
<?php namespace MyApp; use Ratchet\MessageComponentInterface; use Ratchet\ConnectionInterface; class Chat implements MessageComponentInterface { public function onOpen(ConnectionInterface $conn) { } public function onMessage(ConnectionInterface $from, $msg) { } public function onClose(ConnectionInterface $conn) { } public function onError(ConnectionInterface $conn, \Exception $e) { } }
さらに、同様にフォルダ bin/ を作成し、その中にスクリプト(chat-server.php)を作成してください。
chat-server.php
<?php use Ratchet\Server\IoServer; use MyApp\Chat; require dirname(__DIR__) . '/vendor/autoload.php'; $server = IoServer::factory( new Chat(), 8080 ); $server->run();
以上のスクリプトを作成後、ターミナルで以下のコマンドを入力してください。
php bin/chat-server.php
正常に動作するとターミナルには何も表示されないはずですが、以下のようなエラーが表示される場合があります。
Uncaught Error: Class 'MyApp\Chat' not found in 〜
もしこのエラーが表示されたなら composer.phar のアップデートを実行してみてください。アップデートのコマンドは以下のとおりです。
php ~/composer.phar update
正常に動作した場合は control+C で終了させてください。
以上で通信のための準備が整いました。
メッセージ送信の実行
実際に通信をテストするには、まず Chat.php を以下のように書き換えます。
Chat.php
<?php namespace MyApp; use Ratchet\MessageComponentInterface; use Ratchet\ConnectionInterface; class Chat implements MessageComponentInterface { protected $clients; public function __construct() { $this->clients = new \SplObjectStorage; } public function onOpen(ConnectionInterface $conn) { // Store the new connection to send messages to later $this->clients->attach($conn); echo "New connection! ({$conn->resourceId})\n"; } public function onMessage(ConnectionInterface $from, $msg) { $numRecv = count($this->clients) - 1; echo sprintf('Connection %d sending message "%s" to %d other connection%s' . "\n" , $from->resourceId, $msg, $numRecv, $numRecv == 1 ? '' : 's'); foreach ($this->clients as $client) { if ($from !== $client) { // The sender is not the receiver, send to each client connected $client->send($msg); } } } public function onClose(ConnectionInterface $conn) { // The connection is closed, remove it, as we can no longer send it messages $this->clients->detach($conn); echo "Connection {$conn->resourceId} has disconnected\n"; } public function onError(ConnectionInterface $conn, \Exception $e) { echo "An error has occurred: {$e->getMessage()}\n"; $conn->close(); } }
そして、ターミナルのウィンドウを3つ開き、それぞれ以下のコマンドを入力します。
php bin/chat-server.php
telnet localhost 8080
telnet localhost 8080
もし telnet がないと言われた場合は python を利用する以下のコマンドを試してみてください。
python -m telnetlib localhost 8080
実行結果です。一方のtelnetにメッセージを入力すると、他方にメッセージが表示されます。接続状態などは bin/chat-server.php を実行したウィンドウに表示されます。
ブラウザを利用したメッセージの送信
chat-server.php を以下のように書き換えます。
chat-server.php
<?php use Ratchet\Server\IoServer; use Ratchet\Http\HttpServer; use Ratchet\WebSocket\WsServer; use MyApp\Chat; require dirname(__DIR__) . '/vendor/autoload.php'; $server = IoServer::factory( new HttpServer( new WsServer( new Chat() ) ), 8080 ); $server->run();
ターミナルで再度 bin/chat-server.php を実行し、ブラウザのコンソールに以下のjavascriptを入力します。
var conn = new WebSocket('ws://localhost:8080'); conn.onopen = function(e) { console.log("Connection established!"); }; conn.onmessage = function(e) { console.log(e.data); };
今回は GoogleChrome でテストしました。実行結果は以下のとおりです。
ターミナルにブラウザから send によって送信したメッセージが表示されました。
以上、Ratchetの初期設定と、それを利用した通信の例でした。