はじめに
フロントエンドとバックエンドでリアルタイム通信をする必要があったので、どんな選択肢があるのか調べてみました
この記事を読めばリアルタイム通信を実現するWebの技術にどのような種類があるのか、そしてそれらがどういったものなのかをイメージできるようになるかと思います
注意事項:
こちらの記事はあくまでHTTP/HTTPS上のプッシュ技術ということで、MQTTやWebRTCについては言及しないこととします
リアルタイム通信を実現するための手段
Polling
Polling (ポーリング)とはクライアンド側からサーバー側に対して、一定間隔でHTTPリクエストを行う方式のことです。
この方式はデータが更新されているかどうかは関係ありません。シンプルにデータが更新されていれば、更新されている旨のレスポンスを返し、更新されていない場合は更新されていない旨を返します
Polingのメリットとデメリットは以下の通りです
デメリット
- 最大でポーリング間隔分だけ遅延する(リアルタイム性が低くなる)
- データの更新が全くない場合でも一定間隔でリクエストを投げるので、サーバーに負荷がかかる
Long polling(Comet)
Pollingの遅延を解決するために考え出された方式です。また、Long polling(ロングポーリング)はComet(コメット)とも呼ばれ、Pollingを応用したものです。こちらも同様にHTTP通信でやり取りを行います
下記の画像からも分かるように、クライアントからサーバーに対してHTTPリクエストを投げるところはPollingと同じですが、Long Pollingはサーバー側でデータの更新が行われるまでHTTPレスポンスを保留します。データの更新が行われてから初めてHTTPレスポンスを返すのです
また、もしもネットワークエラーなどで接続が失われた場合は、ブラウザはすぐに新しいリクエストを送信します
Long Pollingのデメリットは以下の通りです
- 長時間接続を維持するため、サーバーのリソースを大量に使用する
- 特に大量のクライアントから頻繁にリクエストを受け付けるようなアプリケーションの場合は、このデメリットが顕著に出る
- それぞれが個別のリクエスト・レスポンスであるため、オーバーヘッドが大きくなる
Server-Sent Events(SSE)
SSEはレスポンスをデータの更新があるまで保留にするところはLong Pollingと同じですが、データの更新が起こる度にレスポンスを完結させるのではなく、HTTPのチャンク転送エンコーディングという技術を使って、レスポンスの本文データを、複数のチャンクに分割し、データの更新が行われる度に、クライアントに対してイベントを返します
また、チャンク転送エンコーディングを用いているためSSEは、サーバーからのデータのみを受け取り、クライアントからデータを送信しません。これにより、Long Pllingで問題となっていたサーバーのリソース使用量を減らすことが可能になります
- サーバーからのイベント通知のみサポートしているため、クライアントからサーバーにリクエストを送信できない
- クライアント側は待機状態になるため、新たなHTTP Requestを投げるには別のコネクションが必要になる(ブラウザが同一ドメインに対して同時に保持できるコネクション数は数個しかない)
Websocket
これまでに紹介した中で、最もリアルタイム性が高いのがこのWebsocketです。そのため、チャットアプリやオンラインゲームなどリアルタイム性が必要かつ重要なシーンで使われます
このプロトコルはTCP層に近いためヘッダが軽量です。また、HTTPに比べてサーバーが使用するリソース・通信負荷が少なく、リアルタイム性も高いです。バイナリの送受信も可能です
多数のユーザ接続に対してもサーバへの負荷が少なくスケールがしやすいです
- 通信機器やproxyによっては遮断される場合がある
- 学習コストが高いこと。WebSocketを用いた経験がない場合、実装方法や認証方法、セキュリティなどを学習する必要がある
終わりに
最後までお読みくださりありがとうございました。何かご指摘等あればコメントしていただけると嬉しいです
業務でMQTTも使っているので、またそちらもまとめていきます!