3つの構成要素、1つの目的
Timmyの内部は、かなり実用的な構成です。具体的には、 Flutter をアプリ開発に、 WebRTC をリアルタイムの音声・映像に、そして Firebase を連携の調整に使っています。 すべてをクラウド経由にする巨大なプラットフォームは作りたくありませんでした。各要素が知る情報はできるだけ少なく、それでも確実に連携できるようにしています。
WebRTC:直接接続、標準で暗号化
WebRTC(Web Real-Time Communication)は、赤ちゃん側と保護者側の端末の間で音声・映像を送ります。 最も理想的な場合、データは 2台の端末間で直接、P2Pで流れ、間にメディアサーバーは入りません。
WebRTCの接続では、標準でDTLS-SRTPが使われます。誰かがネットワークパケットを取得しても、音声や映像を読み取ることはできません。この暗号化はプロトコルの一部であり、WebRTCでは無効にすることはできません。
私にとって大切だったのはここです。赤ちゃんのいる部屋の音声・映像を私のサーバーに置くべきではありません。データはあなたの端末同士の間に留まります。
Firebase Firestoreによるシグナリング
WebRTCを始める前に、端末同士がお互いを見つけ、どう接続するかを調整する必要があります。 この処理を シグナリングと呼びます。Timmyでは、そのためにGoogleのクラウドデータベースであるFirebase Firestoreを使っています。
やり取りするのは、接続に必要な技術情報だけです:
- SDPのオファーとアンサー: 端末の機能(対応コーデック、解像度など)を示します。
- ICE候補: 端末同士が接続するために使えるネットワーク経路です。
音声・映像がFirebaseに送られることはありません。Firestoreが運ぶのは、接続に必要な技術情報だけです。 Timmyではこのシグナリング層も暗号化しているため、FirestoreがSDPやICEを平文で受け渡す場所になることはありません。
TURNサーバー:直接つながらないとき
厳しいファイアウォールや一部の携帯通信会社など、直接接続をブロックするネットワークもあります。 その場合、WebRTCには TURNリレー (Traversal Using Relays around NAT)が必要です。
TimmyはまずローカルのTURNサーバーを試し、利用できない場合や負荷が高い場合はCloudflareを予備として使います。 リレーは暗号化されたパケットを転送するだけです。音声や映像の復号鍵を持つことはなく、WebRTCの暗号化もそのまま保たれます。
TURNの認証情報はFirebase Cloud Functionから取得し、有効期限は24時間だけです。 ベビーモニターアプリで恒久的な認証情報を使うのは、私にはリスクが高すぎます。
近くの端末への接続:端末同士を自動で見つける
赤ちゃん側と保護者側の端末の設定を面倒にしないため、Timmyは Nearby Connectionsを使っています。 これは、BluetoothとWi‑Fiを使って端末を検出するためにGoogleが提供している仕組みです。
Timmyの自動ペアリング では、コードを手入力する必要はありません。端末同士が互いを検出し、鍵交換用の共通の待ち合わせ先に接続します。 うまくいかない場合は、4文字のコードを入力できます。 ペアリングコードが端末の外に出ることはありません。Firestoreに見えるのは、ドキュメントIDとして使われる暗号学的ハッシュ(SHA-256)だけです。
匿名認証
TimmyはFirebase Anonymous Authenticationを使っています。初回起動時、各端末には一時的な匿名IDが割り当てられます。 アカウント、メールアドレス、パスワードは必要ありません。このIDはFirestoreのルールを適用するためだけのものです。認証済みの端末だけがセッションデータを読み書きできます。
アーキテクチャ:送る側、受け取る側
Timmyには2つのモードがあります:
- ベビーモード(送信側): 端末がマイクで音を拾い、WebRTC経由で保護者側の端末に送ります。必要に応じてカメラも有効にでき、映像も直接送られます。
- 保護者モード(受信側): 端末が音声・映像を受信し、カメラ映像を表示します。赤ちゃん側の端末に短い声かけを送れるプッシュ・トゥ・トーク機能もあります。
プッシュ・トゥ・トークやカメラのオン/オフなどの操作には、 DataChannelという別のWebRTCチャネルを使います。小さな暗号化メッセージを端末同士で直接送信します。
なぜFlutter?
Flutterは、複数のプラットフォーム向けアプリを作るためのGoogleのフレームワークです。Timmyでは、多くのロジックを一度書けばAndroidとiOSの両方で使えます。 TimmyはAndroidで利用でき、iOS版もリリース間近です。重複するコードが少ないほど、バグが入り込む場所も少なくなります。
まとめ
技術面の原則はシンプルです。Timmyが扱うのは、本当に必要なデータだけです。 WebRTCが音声・映像を保護し、Firebaseが接続の確立を調整します。TURNが扱うのは暗号化されたパケットだけで、Nearby Connectionsがペアリングの手間を減らします。
優れた技術は、日常に自然になじみ、意識されなくなっていくものです。赤ちゃんの部屋をクラウドプロジェクトに変えることなく、きちんと動作します。