WebRTCを使ったJavaScriptによるリアルタイム通信の実装

WebRTCを使ったJavaScriptによるリアルタイム通信の実装

WebRTCは、ブラウザ間でのリアルタイム通信を実現する技術です。本記事では、WebRTCの基本から実際の実装方法までを詳しく解説します。

WebRTCの概要

WebRTCは、音声、ビデオ、データのリアルタイム通信を可能にするためのAPIを提供します。追加のプラグインや専用ソフトウェアを必要としません。

基本的な構成要素

WebRTCは以下の3つの主要なコンポーネントで構成されています。

  • RTCPeerConnection: ピア間の接続を管理
  • MediaStream: オーディオやビデオデータを扱う
  • DataChannel: データ転送を管理

基本的なセットアップ

const peerConnection = new RTCPeerConnection({
  iceServers: [{ urls: "stun:stun.l.google.com:19302" }]
});

ローカルメディアの取得

navigator.mediaDevices.getUserMedia({ video: true, audio: true })
  .then((stream) => {
    document.querySelector("#localVideo").srcObject = stream;
    stream.getTracks().forEach(track => peerConnection.addTrack(track, stream));
  })
  .catch(error => console.error("Error accessing media devices:", error));

SDP(セッション記述プロトコル)の作成

peerConnection.createOffer()
  .then((offer) => {
    return peerConnection.setLocalDescription(offer);
  })
  .then(() => {
    // オファーをリモートピアに送信
    console.log("Local Description Set:", peerConnection.localDescription);
  });

ICE候補のハンドリング

peerConnection.onicecandidate = (event) => {
  if (event.candidate) {
    // ICE候補をリモートピアに送信
    console.log("New ICE candidate:", event.candidate);
  }
};

リモートSDPの設定

peerConnection.setRemoteDescription(new RTCSessionDescription(remoteOffer))
  .then(() => {
    console.log("Remote description set successfully.");
  })

データチャンネルの作成

const dataChannel = peerConnection.createDataChannel("chat");
dataChannel.onopen = () => console.log("Data channel is open");
dataChannel.onmessage = (event) => console.log("Message received:", event.data);

リモートストリームの表示

peerConnection.ontrack = (event) => {
  document.querySelector("#remoteVideo").srcObject = event.streams[0];
};

信号交換の実装

WebRTCのピア同士はSDPやICE候補を交換する必要があります。シグナリングサーバーを用いてこれを実現します。

socket.on("offer", (offer) => {
  peerConnection.setRemoteDescription(new RTCSessionDescription(offer))
    .then(() => peerConnection.createAnswer())
    .then((answer) => peerConnection.setLocalDescription(answer))
    .then(() => {
      socket.emit("answer", peerConnection.localDescription);
    });
});

STUNとTURNサーバーの役割

STUNサーバーはクライアントのパブリックIPを取得し、NAT越えを支援します。TURNサーバーは直接接続ができない場合にデータを中継します。

セキュリティの考慮事項

通信を保護するため、WebRTCではDTLS(Datagram Transport Layer Security)を使用します。また、シグナリングサーバーとの通信もTLSで保護することが重要です。

実用例:ビデオチャットアプリ

以下はWebRTCを使用した簡単なビデオチャットアプリのコード例です。

const localVideo = document.querySelector("#localVideo");
const remoteVideo = document.querySelector("#remoteVideo");

navigator.mediaDevices.getUserMedia({ video: true, audio: true })
  .then((stream) => {
    localVideo.srcObject = stream;
    stream.getTracks().forEach(track => peerConnection.addTrack(track, stream));
  });

peerConnection.ontrack = (event) => {
  remoteVideo.srcObject = event.streams[0];
};

// シグナリング処理
socket.on("offer", (offer) => {
  peerConnection.setRemoteDescription(new RTCSessionDescription(offer))
    .then(() => peerConnection.createAnswer())
    .then((answer) => peerConnection.setLocalDescription(answer))
    .then(() => {
      socket.emit("answer", peerConnection.localDescription);
    });
});

結論

WebRTCは、高速で安全なリアルタイム通信を実現する強力なAPIです。ブラウザ間での低遅延な音声、ビデオ、データ通信を簡単に実現できるため、さまざまな用途に活用可能です。