こんにちは。AI・IoTサービス開発部の青木です。
弊社サービスの OPTiM IoT の開発チームに所属しており、 幅広いデバイスに対応するリモート操作なども視野に入れ、開発を行っています。
OPTiM IoTの目玉機能とも言える、WebブラウザからIoTデバイスのShellにアクセスすることが出来る機能 があり
OPTiM IoTでは リモートシェル
という名称で提供しています。
ここではその リモートシェル
の技術的なアーキテクチャ部分を軽く紹介したいと思います。
リモート操作におけるSSHの大きな課題
リモート操作 = SSH とまでは言いませんが、エンジニアであればまずSSHという言葉が浮かんでくると思います。
みなさんも感じている方は多いと思いますが、OpenSSH Serverなどをデバイスに導入しリモート操作をするには SSH用のポートを開けてあげる必要があります。 他にはVPNを接続するなどの手法がありますが、様々なロケーションで利用されるIoT機器にそのようなネットワークを構築する手段としてはとてもヘビーなものとなります。
リモートシェルについて
リモートシェル
では、そういったIoTデバイスを特別な通信を介さずにSSHのようにターミナル操作がブラウザから可能になります。
リモートシェルの操作画面
お好きなテキストエディタを開いたり、踏み台サーバとして設置しシリアルコンソール接続(screenコマンドなど)も可能です。
リモートシェルのアプリケーションを直接インストールできないIoTデバイスの場合は、踏み台デバイスを用意することでリモート操作を行うことも可能です。
アーキテクチャ
本題ですが、リモートシェルでは基本的にTCPのソケット通信を利用しコマンドの送信や描画用データなどをやり取りしています。
デバイスがAPIサーバとWebsocketで手をつなぎ、コマンド待機状態となります。 ブラウザでは、リモートシェルを利用したい際にAPIサーバにWebsocketコネクションを行い該当のデバイスに予め定義されたコマンドを送信する準備を行います。
このコネクションは事前に定義されたコマンドを送るコネクションで、ここからデバイスのTTYを起動するコマンドを送信します。
起動が完了すると、デバイスから起動完了の返答があるためその状態になればコンソール上のデータがバイナリでやり取りされます。
コネクション上では、PingPongやターミナルのウィンドウサイズ等のメタデータのやり取りも行われていますがフロントエンドでそれらを解釈してターミナル表示を行っています。
Web上でターミナル表示を行う際はxterm.jsを利用しており、Vimなどのテキストエディタもバイナリを解釈して普段利用しているターミナルと同様の操作が可能です。
htopなどの色情報があるものも表示出来ます。
セキュリティと権限管理
デバイス
OPTiM IoTではデバイス認証にJWTを利用した認証を行っています。 詳しい認証方法は以前に記事を執筆していますので、そちらを閲覧ください。
リモートシェル特有のセキュリティ観点としては、ログインユーザの管理があります。 デバイス側では、キッティング時にリモートシェル用ユーザが生成され、デフォルトではそのユーザを利用してログインされます。
ユーザの権限を絞り、別のユーザにリモートシェルの生成ユーザからログインを行うことでパスワード認証をかけるとこも可能ですし、 遠隔操作時に利用するファイルなどのみの権限に予め設定しておくことで、セキュリティリスクをへらすことが可能です。
Webアプリケーション
Webアプリケーション側はOpen ID ConnectとOAuth2による認証認可によりセキュリティを担保しています。 ログインユーザや所属グループによってアクセス制御(Access Control Listによる管理)がされており、許可されたユーザからしか該当の端末に対してリモートシェルを行うことができません。
OPTiM IoTはユーザ及びリソース管理にOPTiM IDを利用しており、OPTiM IDまたはOPTiM ID+ではそれらの権限を細かく設定できる機能を持っていますが、初回導入時などはわかりやすいよう二段階の権限から選択できるようになっています。
- 管理ユーザ
- 一般ユーザ
OPTiM IoTでは基本的にグループに対してデバイスを登録するように作られているため、グループのユーザに対する権限の違いによりリモートシェルシェルへの接続可否が制御されています。 デフォルトでは単純に「管理ユーザ」であれば接続が可能です。
さいごに
全体のアーキテクチャや機能面を紹介させていただきました。
リモートシェルは2019年に私自身が内部のアーキテクチャなどを設計し、開発チーム(別チーム)が実装されたものとなります。 アーキテクチャ設計で考慮したポイントは、なるべく同時接続数が増えても負荷がかからないように接続用中間サーバを設けたり、今後リモートシェル以外の機能が実装された際に同じコントロールコネクションを利用して機能拡張が出来るような構成にしたりといったところです。
他にもアーキテクチャ設計を行ったプロダクトがありますので、またご紹介できればと思います。
オプティムでは、一緒に働く仲間を募集しています。興味のある方は、こちらをご覧ください。