リアルタイムメッセージング

概要

Sora Flutter SDK では DataChannel を利用したリアルタイムメッセージング機能を利用することができます。

同一チャネルに参加しているクライアント同士でリアルタイムなメッセージを送受信することができます。 また、メッセージにはラベルを指定でき、同一チャネル内で複数の種類のメッセージを扱えます。

DataChannel シグナリングを有効にする

リアルタイムメッセージング機能を利用するには、 DataChannel シグナリングが有効になっている必要があります。

設定全体の考え方は DataChannel 経由のシグナリング をご確認ください。

リアルタイムメッセージングの設定をする

Sora Flutter SDK でリアルタイムメッセージング機能を利用するには、接続時の設定で dataChannels を指定する必要があります。

dataChannels には labeldirection を指定します。 label はメッセージの経路を識別するための文字列で、 direction はその経路の方向を指定します。

この label には必ず # を先頭につける必要があります。 # をつけることで、Sora のメッセージング用の DataChannel であることを示しています。

dataChannels はリストなので、複数のラベルを同時に指定できます。

label は送受信時にそのまま使う識別子です。 sendDataChannelMessage() の第 1 引数にも同じ文字列を渡します。

また、ここで指定する dataChannels はアプリ向けメッセージング用です。 signalingnotify などの Sora / SDK 内部用 DataChannel を追加する必要はありません。

final config = SoraConnectionConfig(
  signalingUrls: <String>['wss://example.com/signaling'],
  channelId: 'example-channel',
  role: SoraRole.sendrecv,
  dataChannelSignaling: true,
  dataChannels: <Map<String, Object?>>[
    <String, Object?>{
      'label': '#chat',
      'direction': 'sendrecv',
      'ordered': true,
    },
    <String, Object?>{
      'label': '#notifications',
      'direction': 'recvonly',
      'ordered': false,
      'max_packet_life_time': 3000,
    },
  ],
);

順番保証

リアルタイムメッセージは label 毎に順番保証をするかどうかを指定できます。順番保証をする場合は ordered: true を指定します。

到達保証

リアルタイムメッセージは label 毎に到達保証をするかどうかを指定できます。到達保証をする場合は max_retransmits もしくは max_packet_life_time を指定します。

max_retransmits は再送回数の上限を指定し、 max_packet_life_time は再送の有効期限をミリ秒で指定します。

圧縮機能

リアルタイムメッセージは label 毎に圧縮するかどうかを指定できます。圧縮する場合は compress: true を指定します。

compress: true を指定したラベルでは、 SDK が送信時に自動で圧縮し、受信時に自動で展開します。アプリ側で個別に圧縮処理を書く必要はありません。

メッセージを送信する

メッセージは sendDataChannelMessage()label を指定して送る事ができます。

送信する label は、接続時に dataChannels へ設定したものと一致させます。

メッセージの実体は Uint8List です。文字列や JSON を送りたい場合は、アプリ側で UTF-8 エンコードしてから送信します。

import 'dart:convert';
import 'dart:typed_data';

final data = Uint8List.fromList(
  utf8.encode('{"type":"chat","text":"hello"}'),
);

client.sendDataChannelMessage('#chat', data);

DataChannel が開く前に送信すると取り扱いが分かりにくくなるため、通常は後述の SoraDataChannelOpenEvent を確認してから送信するのが安全です。

メッセージを受信する

メッセージは SoraDataChannelMessageEvent イベント通知で受け取ることができます。 message には、送信したときの labeldata が入ります。

label でメッセージの経路を識別でき、 data で送られてきたデータ内容を受け取ることができます。 dataUint8List のため、文字列や JSON として扱いたい場合は UTF-8 でデコードします。

import 'dart:convert';

conn.events.listen((event) {
  if (event case SoraDataChannelMessageEvent(:final message)) {
    final text = utf8.decode(message.data);
    print('${message.label}: $text');
  }
});

DataChannel が使えるようになったタイミング

利用可能になったことは SoraDataChannelOpenEvent イベント通知で確認できます。

SoraDataChannelOpenEvent は、どのラベルの DataChannel が開いたかを確認するためのイベントです。複数の label を設定している場合は、ラベルごとに監視すると分かりやすくなります。

conn.events.listen((event) {
  if (event case SoraDataChannelOpenEvent(:final event)) {
    print(event.label);
    print(event.direction);
    print(event.compress);
  }
});

リアルタイムメッセージのみを利用する

音声や映像を送受信せず、リアルタイムメッセージ機能のみを利用することができます。ただし、この場合は Sora の設定が必要になります。

この構成では、通常 audio: falsevideo: falsedataChannelSignaling: true に加えて、必要な dataChannels を明示します。

詳細は Sora のドキュメントの DataChannel を利用したメッセージングのみで接続する をご確認ください。