前回の記事に続き、本記事は実装準備編。
SSHクライアントを大きく次の3つに分類して考えます。
- SSHの通信
- コンソール出力画面
- その他のUI
一つずつ解説します。
1. SSH通信
通信部分。実はここは意外と簡単です。
iOS/MacOSであればNMSSH がおすすめですが、Flutterの場合はpub.dev からライブラリを探します。
ライブラリ選定では最終コミット日やGitHub、開発元、LIKESやPUB POINTSの数値を競合ライブラリと相対的に比較、といった点に注目すると優良なものを発掘しやすいです。
ちなみにSSH自体は多くのプログラミング言語で実装できます。例えばPHPでもSSH/SFTPはこちらに記載があります。
WebエンジニアにとってはHTTP以外の通信を書くことは新鮮ですね。
2. コンソール出力画面
ここが鬼門。
画面はANSIエスケープシーケンスに対応する必要があります。例えば半角アルファベット(大文字/小文字)や文字の色、カーソル位置の移動といったものがあります。
これらはエンジニアにとっては馴染みがあると思いますが、ターミナルの画面で表現するために事細かに仕様が決まっています。
ANSIスケープシーケンスについてはこちらのページが分かりやすく一覧でまとまっています。
数年前にターミナルアプリ開発に挑んだ時はこの画面の実装を一から作ろうとしたため途中で挫折してしまいました😅
当時は手探りで進めたこともあって、それなりに実装をしてから予想以上にハードルが高いことに気づいたので同じ轍を踏まないように。。
こちらが良さそうです。
3. その他のUI
最低限の機能であれば1と2だけで問題ありませんが、これだけだと実用的とは言えません。
例えばデスクトップアプリのターミナルに慣れている人にとってはタブで複数開きたいと思いませんか?
加えて、PCと違ってキーボードの入力が充実してない可能性があります。iPadの純正キーボードはどれもESCがありません(私の知る限り)。
他のターミナルアプリを見てみると画面の上部によく使う特殊キーを配置して独自にソフトウェアキーボードを設定する方法を取ったりしているようです。
あとSSHの接続情報のCRUD機能とかも加えると結構ここはやることが増えていきそうですね。
というわけで次こそは実装について触れていきたいと思います。
ちなみに今の実装状況。
うまく出来てそうなのは、
・sudo suなどのインタラクティブモードに対応
・カーソルの上下左右移動、タブを空叩きすると補完が出る
・文字の色が変わる(がっつりは確認できてないけど)
と言ったとこで、複数同時押しの制御に苦戦してます。ctrl + cとかctrl + shift + tabとかのショートカットキーを個別に全部書かなきゃいけない?パターン多すぎ!って状態なんですが、ここらへんちゃんと作らないとvimやnanoエディターがちゃんと動かないので辛いところです。
これはターミナルうんぬんというよりDartの書き方ってとこなのでお勉強って感じですね。。