# ICE コネクションステート機能

## 概要

ICE コネクションステート機能は Sora に ICE コネクションによる状態管理を持たせた機能です。

## 前提

この機能はクライアント側が意識する必要はありません。

## 挙動

Sora は WebRTC が確立した後に TURN 上で ICE コネクションステートを更新し続けます。
ステートの更新には `STUN Binding-Request` と `STUN Binding-Sucess` を利用します。

- Sora は 2.5 秒間隔で `STUN Binding-Request` をクライアントへ送ります- `STUN Binding-Success` が 2.5 秒以内に一度も返ってこない場合、状態を `connected` から `connecting` へ遷移します
- 状態が `connecting` へ遷移した場合、 Sora は 1 秒間隔で `STUN Binding-Request` をクライアントへ送ります- `STUN Binding-Success` が 5 秒以内に一度も返ってこない場合、状態を connecting から disocnnected へ遷移します
  - この 5 秒は `sora.conf` にて `ice_connection_state_disconnected_timeout` で変更可能です
- 状態が `disocnnected` に遷移した場合、 Sora は 50 ミリ秒間隔で `STUN Binding-Request` をクライアントへ送ります- `STUN Binding-Success` が 10 秒以内に一度も返ってこない場合、状態を `disconnected` から `failed` へ遷移します
  - この 10 秒は `sora.conf` にて `ice_connection_state_failed_timeout` で変更可能です
  - このタイミングで `sora.log` に `warning` として `ICE-CONNECTION-STATE-DISCONNECTED` が出力されます
- 状態が `failed` に遷移した場合、Sora はクライアントの接続を切断します- このタイミングで `sora.log` に `error` として `ICE-CONNECTION-STATE-FAILED` が出力されます

## 設定

ICE コネクションステート機能は無効にすることはできません。

ただし、切断や失敗までの判定時間を `sora.conf` にてデフォルト値から変更することが可能です。

### ice_connection_state_disconnected_timeout

この値は Sora が ICE コネクションステートを disconnected へと遷移する際にクライアントからの応答を待つ時間です。

デフォルトでは `5 s` が設定されています。

### ice_connection_state_failed_timeout

この値は Sora が ICE コネクションステートを failed へと遷移する際にクライアントからの応答を待つ時間です。

デフォルトでは `10 s` が設定されています。

## シーケンス図

> **重要**
>
> 図のタイムアウト値はデフォルト値を採用しています。

### connected

正常な接続状態である connected を継続しているシーケンス図です。

seqdiag {
    default_fontsize = 15;
    edge_length = 300;

    === WebRTC 確立 ===

    Sora ->> クライアント [label = 'STUN Binding-Request'];
    Sora <<- クライアント [label = 'STUN Binding-Sucess'];

    ... 2.5 秒 ...

    Sora ->> クライアント [label = 'STUN Binding-Request'];
    Sora <<- クライアント [label = 'STUN Binding-Sucess'];

    ... 2.5 秒 ...

    Sora ->> クライアント [label = 'STUN Binding-Request'];
    Sora <<- クライアント [label = 'STUN Binding-Sucess'];
}

### connected -> connecting

正常な接続状態である connected から一時的に反応が無く connecting 状態へ切り替わるシーケンス図です。

seqdiag {
    default_fontsize = 15;
    edge_length = 300;

    === WebRTC 確立 ===

    Sora ->> クライアント [label = 'STUN Binding-Request', noactivate];

    ... 2.5 秒経過したが反応が無い ...

    === connecting ===

    Sora ->> クライアント [label = 'STUN Binding-Request', noactivate];

    ... 1.0 秒 ...

    Sora ->> クライアント [label = 'STUN Binding-Request', noactivate];

    ... 1.0 秒 ...

    Sora ->> クライアント [label = 'STUN Binding-Request', noactivate];
}

### connecting -> disconnected

一時的に反応が無い connecting の状態が続いたため、
切断判断をするために短い間隔で疎通パケットを送信する disconnected 状態へ切り替わるシーケンス図です。

seqdiag {
    default_fontsize = 15;
    edge_length = 300;

    === WebRTC 確立 ===

    === connecting ===

    Sora ->> クライアント [label = 'STUN Binding-Request', noactivate];

    ... 1.0 秒間隔で 5 秒間送り続けるが反応が無い ...

    Sora ->> クライアント [label = 'STUN Binding-Request', noactivate];

    ... 50 ミリ秒 ...

    Sora ->> クライアント [label = 'STUN Binding-Request', noactivate];
}

### disconnected -> failed

切断判断をするため短い間隔で疎通パケットを送り続けたが、反応が無かったため failed へと切り替わるシーケンス図です。

seqdiag {
    default_fontsize = 15;
    edge_length = 300;

    === WebRTC 確立 ===

    === connecting ===

    === disconnected ===

    Sora ->> クライアント [label = 'STUN Binding-Request', noactivate];

    ... 50 ミリ秒間隔で 10 秒間送り続けるが反応が無い ...

    === 10 秒経過 (failed) ===

    ... Sora はクライアントを切断する ...
}

### disconnected -> connecting -> connected

一定時間、不通になっていたため状態が disconnected になっていましたが、
connecting を経て connected まで状態が戻るシーケンス図です。

seqdiag {
    default_fontsize = 15;
    edge_length = 300;

    === WebRTC 確立 ===

    === connecting ===

    === disconnected ===

    Sora ->> クライアント [label = 'STUN Binding-Request', noactivate];

    ... 50 ミリ秒間隔で 10 秒間送り続ける ...

    Sora <<- クライアント [label = 'STUN Binding-SUCCESS', noactivate];

    === connecting ===

    Sora ->> クライアント [label = 'STUN Binding-Request', noactivate];

    ... 1.0 秒間隔で 5 秒間送り続ける ...

    Sora <<- クライアント [label = 'STUN Binding-SUCCESS', noactivate];

    === connected ===

    Sora ->> クライアント [label = 'STUN Binding-Request', noactivate];

    ... 2.5 秒間隔で送り続ける ...

    Sora <<- クライアント [label = 'STUN Binding-SUCCESS', noactivate];

}
