WebRTCハンズオン 概要編

# はじめに

- この資料は、WebRTCハンズオン勉強会(2016.09.19/2017.04.09/2017.10.16/2018.03.06/2019.01.27)、およびSwiftでWebRTC実装ハンズオン(2017.06.18)用の資料です。
- 資料の全体はこちらのINDEXを参照してください。
  - [WebRTCハンズオン資料 INDEX - Qiita](http://qiita.com/yusuke84/items/de9f0f6d221acec6fc07)
  - [SwiftでWebRTC実装ハンズオン](http://qiita.com/tnoho/items/f5afa3ba749eed9b9716)

----
## WebRTC とは？

#### シンプルな答え

- Web(ブラウザ)でビデオチャットをやるための仕様

#### もう少し詳しい答え

- Web(ブラウザ)でビデオ/オーディオ/データのリアルタイム通信を行うための仕様
    - 双方向、片方向どちらも
- Peer-to-Peer (P2P) で通信可能
- 暗号化の仕組みを持つ
- HTML5の一部、他の要素と組み合わせて利用
- ブラウザだけでなく、Webに繋がるデバイス間で共通利用できることがゴール
    - ※以降の説明で「ブラウザ」とあるのは、適宜「デバイス」と読み替えてください

---
### 何ができるの？

- ブラウザ同志でP2Pで通信する（狭義のWebRTC)
    - [WebRTC 1.0: Real-time Communication Between Browsers](https://www.w3.org/TR/webrtc/)
- カメラの映像、マイクの音声を取得する
    - [Media Capture and Streams]( http://www.w3.org/TR/mediacapture-streams/)
- ビデオ/オーディオの録画/録音を行う
    - [MediaStream Recording](https://www.w3.org/TR/mediastream-recording/)
- 画面/ウィンドウの映像を取得
    - [ScreenCapture](https://w3c.github.io/mediacapture-screen-share/)

<img width="600" alt="webrtc_fig.png" src="https://qiita-image-store.s3.amazonaws.com/0/19403/8f9c8dcb-4d0a-172f-ca4c-742e42d2302a.png">

<!--
![webrtc_fig.png](https://qiita-image-store.s3.amazonaws.com/0/19403/8f9c8dcb-4d0a-172f-ca4c-742e42d2302a.png)
-->

---
### どこで使えるの？

<!--
<img width="600" alt="webrtc_table.png" src="https://qiita-image-store.s3.amazonaws.com/0/19403/0cf8f366-fee5-e3a6-3161-5204a49d67df.png">
-->

<!--
![webrtc_handson_table_201710.png](https://qiita-image-store.s3.amazonaws.com/0/19403/607c1a0f-3c2a-e99d-6878-832362289d41.png)
-->

<!--
![webrtc_platform.png](https://qiita-image-store.s3.amazonaws.com/0/19403/c16e4bf2-445e-27ac-b621-e5cbbfc8c82e.png)
-->

| |Windows|Mac|Linux|Android|iOS|
|:--|:--:|:--:|:--:|:--:|:--:|
|Chrome|⚪︎|⚪︎|⚪︎|⚪︎|×|
|Firefox|⚪︎|⚪︎|⚪︎|⚪︎|×|
|Edge|⚪︎|ー|ー|？|？|
|IE|×|ー|ー|ー|ー|
|Safari|ー|⚪︎|ー|ー|⚪︎|
|App|⚪︎|⚪︎|⚪︎|⚪︎|⚪︎|

- ※ Mac OS X / iOS のSafariは、2017秋のSafari 11から対応(H.264のみ)。[(What's new in Safari)](https://developer.apple.com/library/content/releasenotes/General/WhatsNewInSafari/Safari_11_0/Safari_11_0.html)
    - promiseベースの新しいAPIのみ対応
    - カメラ/マイクへのアクセスにはhttps:// 必須。Mac OS X の場合は開発者メニューから http://を使えるようにできる
- Edge：ORTCに対応、WebRTCにCreators Update(2017.04.11)で対応（[参考記事](https://blogs.windows.com/msedgedev/2017/01/31/introducing-webrtc-microsoft-edge/#g7X4CokcE4hMWVYm.97))。STUN利用やDataChannelには未対応
- ？：iOS / Android 向けEdgeのリリース予告あり。対応状況未確認
- ×: IEはサードパーティプラグイン有

---
### 誰が決めているの？

- API ... [W3C](http://www.w3.org/2011/04/webrtc/)
    - ブラウザからどうやって使うか
- アーキテクチャ、通信の仕様 ... [IETF](https://tools.ietf.org/wg/rtcweb/)
    - 映像、音声のコーデック（圧縮方式）
    - 実際のデータの送り方（プロトコル）

### 誰が実装しているの？

- 本家 [WebRTC.org](https://webrtc.org) ... Google, Mozilla など 
- 対抗 [OpenWebRTC](http://www.openwebrtc.org)（※休眠中） ... Ericsson など

---
## P2P通信行うまで(1-1)：シグナリング
P2P通信を行う前には

- 通信相手の情報を知らなければならない
    - 電話なら、相手の電話番号
    - WebRTCなら、相手のIPアドレスや通信ポート
- さらに、通信する内容を合わせる必要がある
    - 電話なら、日本語で話すのか英語で話すのか
    - WebRTCなら、映像/音声の有無とコーデック、などなど

![signalling1.png](https://qiita-image-store.s3.amazonaws.com/0/19403/588b6a93-5df2-e235-ffcf-14bce5e50c8d.png)


---
## P2P通信行うまで(1-2)：シグナリング

※ これをやり取りするのが「シグナリング」

- 方法はWebRTCでは決められていない（自由に選べる）
- シグナリングサーバーを用意するのが一般的
- SDPと呼ばれる形式でやり取りする
    - [SDP for WebRTC - From Basics to Maniacs -](http://www.slideshare.net/iwashi86/20150311-web-rtcmeetup7sdp)

![signalling2.png](https://qiita-image-store.s3.amazonaws.com/0/19403/e4472180-b25c-5f86-1cc4-cd8662f7cb24.png)

---
## P2P通信行うまで(1-3)：Offer / Answer

- 通信を始める側から送るSDP: Offer
- 通信に応答する側から送るSDP: Answer

<img width="759" alt="offer_answer.png" src="https://qiita-image-store.s3.amazonaws.com/0/19403/a7952bcb-c08e-28ef-0e6b-5d93282e68e8.png">

---
## P2P通信行うまで(2-1)：NAT越え

- P2P通信は、お互いのIPアドレスとポートを指定して行う
- 実際の環境ではNATが挟まるケースが多い。例えば
    - 自宅内と外側
    - 会社内と外側
    - 異なるモバイルネットワーク
- NATが入ると、相手から見えるIPアドレスとポートが変わってしまう
    - 自分では分からない

![nat.png](https://qiita-image-store.s3.amazonaws.com/0/19403/b3080b8f-ad8c-585a-7487-b3adc1318f81.png)

---
## P2P通信行うまで(2-2)：NAT越え
- 外部から見たIPアドレスとポートを知るための仕組み ... STUN
- NATで変換されたIPアドレス/ポートをSTUNサーバーに教えてもらう

![stan.png](https://qiita-image-store.s3.amazonaws.com/0/19403/333d3ef3-e100-783c-3f8e-45c54b4789a2.png)

---
## P2P通信行うまで(2-3)：NAT越え
- STUNサーバーから取得した情報を、通信相手と交換する

![stan2.png](https://qiita-image-store.s3.amazonaws.com/0/19403/df82a8a4-f682-2021-cb44-dbb6341dc964.png)

※実際に繋ぐにはUDPホールパンチングという手法が用いられる（今日は省略）

---
## P2P通信行うまで(3)：Firewall越え

- WebRTCではUDP/IPを利用、ポート番号は動的に決定
- Firewallによって、ポートが制限されたり、UDPが禁止されることがある
- このようなケースでも通信を可能にする仕組み ... TURN
    - TURNサーバーが全てのパケットを中継する
    - ポート範囲の制限や、固定が可能
    - UDPだけでなく、TCPでの通信も可能
    - パケットは暗号化されたまま扱う

![turn.png](https://qiita-image-store.s3.amazonaws.com/0/19403/a304038d-09ed-2c98-5356-19c755f6059b.png)

---
## STUN/TURNとシグナリング

シグナリングで交換する情報

- SDP
- STUN/TURNを含む通信経路の情報: ICE Candidate
    - ローカルネットワーク内の直接通信
    - STUNで取得した外部IPアドレス/ポートを使ったNAT越え
    - TURNサーバー経由

適切な通信経路を選ぶ仕組み → ICE

参考：[WebRTCのICEについて知る](http://www.slideshare.net/iwashi86/webrtcice)

---
### 2つの方式： Vanilla ICE と Trickle ICE

- 経路情報であるICE Candidateは、非同期に収集される
- Vanilla ICE
    - 全てのICE Candidateが出揃ってから、SDPに含めて交換する方式
    - 処理がシンプル
- Trickle ICE
    - 初期SDPを交換し、ICE Candidateを発見するたびに順次交換する方式
    - 全てのICE Candidateを収集する前に、P2P通信に成功する可能性がある

---
### Vanilla ICEの場合

![vanilla.png](https://qiita-image-store.s3.amazonaws.com/0/19403/ee0c6db6-a142-509e-5500-4d5342003702.png)

---
### Trickle ICEの場合

![trickle.png](https://qiita-image-store.s3.amazonaws.com/0/19403/ff526e1a-667b-9f90-ee6f-7e33d94a5482.png)


---
## 参考資料

* WebRTC.org https://webrtc.org
* HTML5Experts.jp WebRTC入門2016 https://html5experts.jp/series/webrtc2016/
* WebRTC Boot Camp (WebRTC Conference Japan 2016) 事前公開版 http://www.slideshare.net/You_Kinjoh/webrtc-boot-camp-webrtc-conference-japan-2016)
* WebRTC入門+最新動向 http://www.slideshare.net/rotsuya/intro-webrtcppt
* WebRTC/ORTCの最新動向まるわかり！ http://www.slideshare.net/yusukenaka52/webrtcortc
* WebRTC Update 2016 Summer http://qiita.com/yusuke84/items/7c0d7556228caff6cf71

<!--
| |Windows|Mac|Linux|Android|iOS|
|:--|:--:|:--:|:--:|:--:|:--:|
|Chrome|⚪︎|⚪︎|⚪︎|⚪︎|×|
|Firefox|⚪︎|⚪︎|⚪︎|⚪︎|×|
|Edge|⚪︎|ー|ー|？|？|
|IE|×|ー|ー|ー|ー|
|Safari|ー|⚪︎|ー|ー|⚪︎|
|App|⚪︎|⚪︎|⚪︎|⚪︎|⚪︎|

-->

---
### 参考：コーデックについて

- ビデオコーデック
    - [仕様では](https://tools.ietf.org/html/rfc7742) VP8, H.264が必須
    - デスクトップ版 Chrome, Firefoxでは VP9をデフォルトに
    - Safariでは H.264 のみサポート
    - 次世代としてAV1が有望視 .. by [Alliance for Open Media](http://aomedia.org/)

- オーディオコーデック
    - [仕様では](https://tools.ietf.org/html/rfc7874) Opus, G.711(PCMU/PCMA)が必須

---

### 参考：WebRTCのトポロジー

- P2P (Peer-to-Peer) ... ブラウザ同士が直接通信、フルメッシュ
- MCU (Multipoint Control Unit) ... サーバー側で映像/音声を合成、再圧縮
- SFU (Selective Forwarding Unit) ... サーバー側で映像/音声を配布

---
#### P2P
![webrtc_p2p.png](https://qiita-image-store.s3.amazonaws.com/0/19403/50350a28-811c-9c6f-6d75-883757aaecd6.png)

---
#### MCU
![webrtc_mcu.png](https://qiita-image-store.s3.amazonaws.com/0/19403/7242f5b9-6be8-26dd-39fc-6f3d5d449755.png)

---
#### SFU
![webrtc_sfu.png](https://qiita-image-store.s3.amazonaws.com/0/19403/e0b5e49d-fe64-3ba3-7740-10e48b2519f0.png)


---

## なにかご質問は？

## それでは、準備に進みましょう

- [WebRTCハンズオン：準備編](http://qiita.com/massie_g/items/6141a1020dd8bdf6574e)