Azure IoT HubでEdge端末の通信断をCloud側から検知・通知する ― Event Gridと最終受信時刻を組み合わせる
Azure IoT Hubへ接続しているEdge端末で、
Edge PC
↓
Network障害
↓
Azure IoT Hubへ接続できない
という状態になったとき、
「通信できなくなったことをどうやって検知するか」
という問題があります。
Edge端末自身から、
通信できません
とCloudへ通知できれば簡単ですが、そもそもCloudとの通信が切れているため、その通知自体を送れません。
そこで今回は、
Azure IoT Hub
↓
Event Grid
↓
Logic App
↓
Notification
という構成を使い、
Edge端末から通信が来なくなったことをCloud側から検知する設計
を整理します。
ポイントは、DeviceDisconnectedだけで判断するのではなく、
DeviceDisconnected
+
最終Data受信時刻
+
一定時間のGrace Period
を組み合わせることです。
想定環境
今回の構成では、現場に設置したLinux Edge PCからAzure IoT HubへDataを送信しています。
Modality
↓
Edge PC
↓
施設Network
↓
Internet
↓
Azure IoT Hub
Cloudとの通信には、
AMQP over WebSocket
TCP 443
を使用しています。
また、Edge PCとは別にExternal Monitorを設置し、Local側では、
Ping
Heartbeat
Telemetry
rsyslog
netconsole
などを監視しています。
今回追加するのは、
Edge PCからAzureまで正常に通信できているかをCloud側から監視する仕組み
です。
結論:通信断はEdge側ではなくCloud側から検知する
通信断が発生すると、
Edge PC
↓
Network Disconnect
↓
「通信断です」とCloudへ送信
↓
送信できない
となります。
そのため、
Edge PCから異常を通知する
のではなく、
Cloud側で
「正常時に来ていた通信が来なくなった」
ことを検知する
という設計にします。
今回の基本構成は以下です。
Edge PC
│
│ AMQP over WebSocket / TCP 443
│
▼
Azure IoT Hub
│
│ DeviceDisconnected
│
▼
Azure Event Grid
│
▼
Logic App
│
├─ 一定時間待機
├─ 再接続確認
├─ 最終Data受信時刻確認
│
▼
Communication Failure判定
│
▼
Notification
ただし、
DeviceDisconnected
↓
即通知
にはしません。
これが今回の重要なポイントです。
1. DeviceDisconnectedで通信断を検知する
Azure IoT Hubでは、Deviceの接続状態に関するEventを扱えます。
例えば、
DeviceConnected
DeviceDisconnected
です。
これをEvent Gridへ連携することで、
DeviceDisconnected
↓
Event Grid
↓
Logic App
という処理を開始できます。
つまり、Edge PC側へ、
通信断を検知する処理
を追加するのではありません。
Cloud側で、
「DeviceとのConnectionが切れた」ことをTriggerにする
という構成です。
2. DeviceDisconnectedですぐ通知してはいけない
ここで、
DeviceDisconnected
↓
Mail送信
としてしまうと問題があります。
Networkでは、一時的な切断が発生することがあります。
例えば、
Router切替
数秒間のNetwork揺らぎ
IoT Edgeの再接続
一時的なWAN断
などです。
例えば、
12:00:00 Disconnect
12:00:05 Reconnect
だった場合でも、即時通知では障害Mailが送信されます。
そのため、
Disconnect
↓
即通知
ではなく、
Disconnect
↓
一定時間待つ
↓
まだ異常が続いているか確認
とします。
3. Grace Periodを設ける
基本的な考え方は以下です。
DeviceDisconnected
↓
Timer Start
↓
3分待機
↓
復旧した?
復旧していれば、
通知しない
復旧していなければ、
Communication Failure
↓
通知
とします。
例えば、
2分
3分
5分
などのGrace Periodを設定します。
何分が適切かは、
Systemとして何分間の通信断まで許容できるか
によって決めます。
つまり監視したいのは、
通信が一度切れた
ことではなく、
許容時間を超えて通信できていない
ことです。
4. Connection StateだけではSystem正常とは判断できない
もう一つ注意する必要があります。
例えば、
IoT Hub Connection
↓
Connected
だったとしても、
Application側でData送信が止まっている可能性があります。
例えば、
OS
↓
正常
IoT Edge
↓
Connected
Application Module
↓
停止
という状態です。
この場合、
Connection = Connected
でも、
Cloudへ必要なDataは届きません。
つまり、
Connection正常
=
System正常
ではありません。
そこで、
Cloud側では、
Connection State
だけでなく、
Last Data Received
も確認します。
5. 最終Data受信時刻を監視する
Edge PCから定期的にDataを送信しているSystemであれば、
Cloud側で、
Device A
Last Received:
12:00:05
のように最終受信時刻を管理できます。
例えば現在時刻が、
12:05:05
だった場合、
現在
12:05:05
Last Received
12:00:05
Difference
5 minutes
となります。
つまり、
5分間Dataが届いていない
と判断できます。
Connection Stateよりも、
Systemとして実際にDataをCloudまで届けられているか
を見るための情報になります。
6. DeviceDisconnectedとData未受信を組み合わせる
実運用では、
DeviceDisconnected
だけで通信障害を確定させません。
例えば、
① DeviceDisconnected
↓
通信異常の可能性を検知
② 一定時間Dataが届かない
↓
異常が継続していることを確認
という二段階で判断します。
例えば、
DeviceDisconnected
↓
3分待つ
↓
新しいDataあり
↓
復旧済み
↓
通知しない
一方、
DeviceDisconnected
↓
3分待つ
↓
新しいDataなし
↓
Communication Failure
↓
通知
とします。
これによって、一時的なNetwork揺らぎによる不要な通知を減らせます。
7. Data未受信も独立して監視する
逆のケースもあります。
DeviceDisconnected
が発生していなくても、
Applicationだけ停止する可能性があります。
例えば、
OS
↓
正常
IoT Edge
↓
Connectionあり
Application Module
↓
停止
Data
↓
送信されない
という状態です。
このケースではConnection Monitoringだけでは検知できません。
そのため、
一定時間Dataが届いていない
という条件も、独立したMonitoringとして持たせます。
整理すると、
Connection Monitoring
│
└─ DeviceDisconnected
Data Monitoring
│
└─ Last Received Time
です。
Connection Monitoringでは、
Network
IoT Hub Connection
の異常を検知します。
Data Monitoringでは、
Application
Module
Data Pipeline
を含めて、
Systemとして本当にDataを送れているか
を確認します。
8. 通知には障害調査に必要な情報を入れる
通知内容が、
通信エラーです
だけでは、障害調査に十分ではありません。
最低限、
Device ID
検知時刻
Disconnect検知時刻
Last Data Received
通信断継続時間
現在のStatus
などを入れておきます。
例えば、
Device:
Edge-PC-001
Status:
Communication Lost
Disconnected:
02:15
Last Data:
02:14:55
Duration:
5 minutes
です。
これによって通知を見た時点で、
どの端末か
いつから止まっているか
最後にDataが来たのはいつか
を確認できます。
9. 復旧もMonitoringする
通信断を通知したら、
復旧も検知します。
例えば、
02:15
Communication Lost
02:23
Communication Restored
です。
復旧判定には、
DeviceConnected
だけでなく、
Data受信再開
も確認できます。
例えば、
Communication Failure
↓
Reconnect
↓
Data受信再開
↓
Recovered
です。
必要であれば、
Recovery Notification
も送ります。
これによって、
障害通知は来た
でも現在も止まっているのか分からない
という状態を防げます。
10. 同じ障害を何度も通知しない
長時間の通信断では、重複通知にも注意します。
例えば通信断が30分続いたとき、
5分経過
↓
通知
10分経過
↓
通知
15分経過
↓
通知
となると運用しにくくなります。
そこでDeviceごとに、
NORMAL
ALERT
RECOVERED
のような状態を管理します。
例えば、
NORMAL
↓
異常検知
↓
ALERT
↓
初回通知
とします。
通信断が続いている間は、
ALERT
のままなので、初回通知を繰り返しません。
復旧したら、
ALERT
↓
RECOVERED
↓
NORMAL
へ戻します。
つまり、
Eventが発生するたびに通知するのではなく、状態が変化したときに通知する
という考え方です。
11. Local Monitoringと組み合わせる
Cloud Monitoringだけでは、障害箇所までは分かりません。
そこでLocal Monitoringと組み合わせます。
例えばCloud側で、
Communication Lost
を検知したとします。
一方、現場のExternal Monitorでは、
Ping
OK
Heartbeat
OK
Telemetry
OK
だった場合、
Edge PC自体は動いている可能性が高くなります。
その場合は、
Internet回線
施設Firewall
DNS
WAN Route
Azureまでの経路
などを優先して調査できます。
逆に、
Cloud
Communication Lost
External Monitor
Ping NG
Heartbeat NG
であれば、
Edge PC Freeze
Power Loss
NIC
Local Network
など、より下位Layerの障害を疑えます。
12. Local MonitoringとCloud Monitoringの役割
役割を整理すると、
| Monitoring | 確認するもの |
|---|---|
| Local Ping | Edge PCまでNetwork的に到達できるか |
| Heartbeat | Application / OSが動作しているか |
| Telemetry | CPU・Memory・温度など |
| rsyslog | OS / Application Log |
| netconsole | Kernel異常 |
| IoT Hub Connection | Azureまで接続できているか |
| Last Data Received | Cloudまで実際にDataが届いているか |
重要なのは、
一つのMonitoringですべての障害を判断しない
ことです。
複数のLayerを組み合わせて、
どこまでは正常だったのか
を見ることで、調査範囲を絞れます。
13. MonitoringをLayerで整理する
今回の構成をLayerで整理すると、
Application
│
├─ Cloud Data受信
└─ Local Heartbeat
IoT / Cloud Connection
│
└─ IoT Hub / Event Grid
OS
│
├─ Telemetry
└─ rsyslog
Kernel
│
└─ netconsole
Network
│
├─ Local Ping
└─ Cloud Connection
Hardware
│
├─ SMART
├─ watchdog
└─ External Monitor
となります。
障害が発生したとき、
Cloud Data
NG
Local Heartbeat
OK
Ping
OK
であれば、
ApplicationやOS全体ではなく、
Cloudまでの通信経路
を優先して調査できます。
14. 実際に通信を切って試験する
Monitoringは、設定して終わりではありません。
実際にNetworkを切って確認します。
今回のCloud通信は、
AMQP over WebSocket
TCP 443
なので、Test環境でAzureへ接続できない状態を意図的に作ります。
確認する項目は例えば以下です。
1. Edge PCからAzureへの通信を停止
2. IoT Hub側でDisconnectを検知
3. Event GridへEventが届く
4. Logic Appが起動
5. Grace Period待機
6. Last Data Receivedを確認
7. Communication Failure判定
8. Notification送信
復旧試験も行います。
Network Restore
↓
Reconnect
↓
Data送信再開
↓
Recovered
↓
Recovery Notification
まで確認します。
15. Cloud Monitoringにも限界がある
Cloud側のMonitoringも万能ではありません。
今回の構成では、
IoT Hub
Event Grid
Logic App
Notification Service
を使用しています。
そのためAzure側のServiceに障害が発生した場合、
Device Disconnect通知そのものが正常に動かない可能性があります。
そこで、
Edge側Monitoring
Local External Monitoring
Cloud Monitoring
を分離します。
Azure Platform側の障害については、
Service Health
Resource Monitoring
など、Device Monitoringとは別の監視も必要になります。
最終的な構成
今回追加したCloud Monitoringは以下です。
Edge PC
│
│ Data
│
▼
Azure IoT Hub
│
├─ DeviceDisconnected
│
▼
Event Grid
│
▼
Logic App
│
├─ Grace Period
├─ Connection確認
├─ Last Data Received確認
│
▼
Communication Failure
│
▼
Notification
そして復旧時には、
Reconnect
+
Data受信再開
↓
Recovered
とします。
まとめ
Edge PCとAzureとの通信が切れた場合、
Edge PC自身から、
通信できません
とCloudへ通知することはできません。
そこで、
正常時に来ていた通信やDataが来なくなったことをCloud側から監視する
ようにします。
今回のポイントは、
DeviceDisconnected
だけで判断しないことです。
DeviceDisconnected
↓
Connection異常の可能性
+
Last Data Received
↓
実際にDataが止まっているか確認
+
Grace Period
↓
一時的なNetwork揺らぎを除外
と組み合わせます。
さらに、
NORMAL
↓
ALERT
↓
RECOVERED
という状態管理を行うことで、重複通知を防ぎます。
そしてLocal Monitoringと組み合わせれば、
Local OK
Cloud NG
↓
WAN / Firewall / DNS / Internet側を疑う
あるいは、
Local NG
Cloud NG
↓
Edge PC / Power / NIC / Local Network側を疑う
という切り分けもできます。
通信断Monitoringで重要なのは、
異常を知らせるための通信そのものが使えなくなる可能性があるなら、通信の反対側にも異常判定を持たせること
だと考えています。