ターミナルプログラムを使用してキーストローク転送をどのようにシミュレートできますか?

ターミナルプログラムを使用してキーストローク転送をどのようにシミュレートできますか?

仮想的にターミナルプログラムにキーストロークを送信する必要があります(例:またはEmacs)。

私はこのようなことをしたい:

echo -e 'iHello, world!\e' | vi

それからそこに次のバッファーでセッションを開きます。

Hello, world!
~
~
~
~
~

しかし、これはうまくいきませんキーストロークを読み取れない標準入力

次のエラーが発生します。

ex/vi: Vi's standard input and output must be a terminal

キーボードから直接入力したように、一部のテキスト文字列をターミナルプログラムに送信するにはどうすればよいですか?

答え1

これは一般的にexpectそれ:

expect -c 'spawn -noecho vi; send "iHello World!\r\33"; interact'

普及するexpectperlまたは以前にTCL用に書かれていますが、現在同様のモジュールpython~のためperlまたはpythonも可能。

別のオプションは、ttyデバイスでioctlを実行してTIOCSTI入力キューに文字を挿入することです(一度に1バイト)。

perl -le 'require "sys/ioctl.ph";
          ioctl(STDIN, &TIOCSTI, $_) for split "", join " ", @ARGV
         ' $'iHello World!\r\e'; vi

これは、ターミナルエミュレータとアプリケーション(ここでvi)の間に追加の疑似ターミナル層を防ぐことができるという利点があります。

答え2

@Stéphane ChazelasのPerlの例に基づいて、スクリプトまたはコマンドラインから次のものを使用できます。

stty -echo; perl -le 'require "sys/ioctl.ph"; ioctl(STDIN, &TIOCSTI, $_) for split "", join " ", @ARGV ' `_cmds_` ;stty echo; _app_

最終放棄したらアプリ出力ガイドライン入力キュー(カーネルではこれを呼び出す)、現在のコンソールシェル、またはshellコマンドラインを編集するアプリケーションに表示されます。stty画面上のすべての(全二重)エコーを停止します。

メモ:技術的には、これは明示的に「アナログキーを押す」ではありません。

関連情報