~llamerada/memo/スマートフォン用の表示で見る~llamerada/memo/この広告は、90日以上更新していないブログに表示しています。Clientを利用するSocket.IOはwebブラウザ上のアプリケーション間でリアルタイム性の高い通信を実現するためのNode.jsのライブラリです。ClientはそのSocket.IOのサーバへネイティブアプリから接続するためのライブラリです。コレを利用するとwebとネイティブアプリで同じサーバを介して通信ができます。UnixのSocket通信とは異なりストリームではなく、1つ1つのメッセージ単位で授受します。インストール方法の一部に不足があったため編集しました。Clientがhttpsに対応しました。以下に関連blogを書きました。Clientを利用するにはver1.0以降が必須です。以下sio(C++のnamespaceより)と省略Node.jsやNode.jsでのSocket.IOの利用方法についてはこの記事では触れません(他にわかりやすい資料がいっぱいあるため)。インストール(C++版だけ)sioはBoostを使うので、Boostを用意します。バージョン指定は特になかったので最新版を入れました。boostパッケージ等はまだ無いので、gitからclone、コンパイルします。インストールしたboostの格納先に応じてcmakeのオプションは変更してください。←ヘッダファイル、ライブラリが格納されているtestサンプルプログラムwebブラウザで入力したコマンドをサーバ経由でネイティブアプリで実行して結果を表示するサンプルプログラムを作りました。認証しないユーザでコマンドを実行できるので、このままサービスを公開するなどということは絶対しないでください。全体では以下の図のような動作をします。サンプルプログラムなため、sioのエラー処理以外でのパケットのフォーマットチェックなどは省いています。サンプルプログラムのコンパイル、起動方法gitからのclone、コンパイルは以下のようになります。makeサーバの起動は以下のとおりです。index.js待機開始C++プログラムの起動は以下のとおりです。<マシン名>待機開始webブラウザからhttp://localhost:8000/などにアクセスします。テキストボックスにlsなどのコマンドを入力し、実行ボタンを押すと、以下のように実行結果が表示されます。C++での処理の流れSampleClient::runがメインの処理になっています。on_close、on_fail、on_openはrunの最初でsioにリスナとして登録しておきます。connectでの接続処理connectに接続先URLを渡すと、別スレッドで接続処理の待ち合わせが行われます。socketの取得は接続処理が終わった後でなければなりません。接続処理が終わると別スレッドでon_openが呼ばれます。そのため、mutexとcondition_variable_anyを使ってon_openでの処理が終わるまでメインスレッドを待たせています。sio_cond.notify_all();}onでのリスナの登録web版同様、onメソッドでリスナを登録します。std::placeholders::_1));登録される側は以下のようになっています。処理内容は受信処理の欄で詳しく説明します。sio_cond.notify_all();}emitでの送信処理メッセージの送信は以下のとおりです。C++ではJavaScritptでのJSONのような柔らかい(?)構造は取れないため、std::mapを使ってobject相当の構造を作ります。詳しくはJSONに対応するデータ構造の欄にまとめました。sio::messageさえ作れれば送信のしかたはweb版と同じです。send_data);受信処理sioではpooling(受信ソケットを監視するなど)の処理を入れる必要はありません。ライブラリ内で別スレッドが起動してサーバとの通信を監視しています。onメソッドで登録した関数も接続処理と同様、別スレッドで動きます。サンプルでは受信時はメインスレッドと共有しているキューにデータを登録して、メインスレッドでキューにデータが入っていた場合に解析することで、マルチスレッドでの排他制御を回避しています(イベント受信時と解析時のみ考慮している)。sio_cond.notify_all();}メインスレッドではキューが空の場合はon_runでsio_cond.notify_all()が呼び出されるまでまち、再度キューの状態を確認します。キューにデータが入っていることが確認できたら処理に移ります。処理終了のタイミングでキューからデータを削除します。sio_queue.pop();}この方式ではサーバからの受信とキューの消化処理を平行して実行しません。並行した処理が無いため、マルチスレッド由来のデッドロックは不安定な状態は発生しませんが、on_runで処理を行う場合に比べて性能が低いです。作りたいアプリケーションの構造によって適宜構造を考えたほうが良いです。今回はsioメインのサンプルなので一番安全そうな処理にしたつもりです。string_messageなど)に格納しています。sio::message::ptrを戻すのようにします。src/sio_message.hで定義されており、まとめると以下のとおりです。flag_binarynullの取り扱いJavaScriptでオブジェクトにnullを設定した場合、C++側ではsio::message::ptrがnullptrを指しています。そのため、型の判定は以下のようになります。std::endl;}boolの取り扱いbool値の取り扱いには対応していないようです。JavaScript側でbool値を設定した場合、C++側ではnullとなってしまいました。既存プログラムでbool値がある場合は、プログラムを書き換えるか、Node.jsで判定して整数に変換してからクライアントに渡すなどの対応が必要です。その他httpsにはまだ対応していないです。現在実装中だそうです。github.comクライアントがネイティブだけでサーバに大したロジックが不要であればFlatBuffersを梱包して渡すのもありな気がします。ルーティング情報とバイナリ(FlatBuffers)だけを持ったパケットをNode.js+Redisで転送するだけとか。Clientが早くもTLSに対応しました。EntriesArchiveはてなブログをはじめよう!llamerad-jpさんは、はてなブログを使っています。ブログを報告するスターをつけました引用をストックしましたストック一覧を見る閉じる引用するにはまずログインしてくださいログイン閉じる引用をストックできませんでした。再度お試しください閉じる限定公開記事のため引用できません。