4

対話型のコマンド ライン プログラムを呼び出して、キーボードから直接入力する方法と、名前付きパイプから入力する方法を見つけようとしています。私の目標は、これを MATLAB で動作させることですが、Bash はサンプルと同じように機能すると思います。つまり、Bash を起動して実行すると、コマンドを入力したり、上向き矢印を使用して履歴を表示したり、名前付きパイプにコマンドを送信したりできます。私はこれを数日間見回していじっていましたが、これまで試したことは何もうまくいきませんでした.

たとえば、https://serverfault.com/questions/171095/how-do-i-join-two-named-pipes-into-single-input-stream-in-linuxには、次のようなことを提案する役立つスレッドがあります。これ:

mkfifo alt_in
(tail -f alt_in & cat) | bash

これは、バックスペースまたは矢印キーを使用しようとすると正しく機能しないことを除いて、私が探しているものとほぼ同じです。(これは、通常 bash の readline ライブラリによって処理されるキーストロークをインターセプトしているためだと思いcatますか?) 他の提案はありますか?

最終的には、MATLAB プロセスを起動して、TextMate からコマンドを送信できるだけでなく、ターミナルで操作できるようにしたいと考えています。私は仕事で MATLAB を使用していますが、その GUI やエディターはあまり好きではありません。

2010 年 12 月 19 日編集

すべての非常に役立つ提案をありがとう!興味のある方のために、この結果を要約したいと思います。を調べましrlwrapたが、私の目標は誰でも使用できる TextMate バンドル内でこれを機能させることだったので、非標準のユーティリティ (最初に言及する必要があった) に依存することをためらっていました。私も簡単にチェックしましexpectunbufferが、まあ、かなり複雑に思えて、そこに飛び込む勇気がありませんでした.

screenこれは非常にうまく機能しました-以下に示すように、ターミナルを開いて start screen、 startを実行すると、TextMate コマンドmatlab -nodesktopを使用して、選択したテキストを Matlab に送信することができました。screen -X ...私が気づいたこのアプローチの欠点は次のとおりです。

  1. 1,024 文字を超えるテキスト ブロックを送信すると、`screen` からエラーが発生しました。それ以上は保持できないバッファーがどこかにあると思いますが、それを追跡するのに時間をかけませんでした。
  2. 画面には独自のスクロールバック バッファがあるため、ターミナルのスクロールバーはほとんど役に立たなくなります。たぶん、これがどのように機能するかを変更するオプションがありますか?
  3. Control-A は `screen` のコマンド キーストロークです。コマンドキーを再バインドしない限り、行頭への移動には使用できません。

をいじっていscreenたときに、私が尋ねた質問はパイプや STDIN などの接続に関するものでしたが、実際には、TextMate からターミナルにテキストを取得するという非常に特殊なケースについてのみ気にしていることに気付きました。そこで、AppleScript を使ってこれをやってみようと思ったのですが、驚くべきことに、それは私が試した他のどの方法よりも簡単で堅牢であることがわかりました。選択したテキストまたは現在の行を入力として取り、次を含む TextMate コマンドを作成します。

#!/usr/bin/env osascript

set input_command to do shell script "cat"

tell application "Terminal"
    do script input_command in window 1
end tell

そして、MATLAB が最前面のターミナル ウィンドウにある限り、うまく機能します。(MATLAB を実行している [ターミナル] タブを検索することもできますが、わかりやすくするために除外しました。)

この話の教訓は、もっと具体的な質問をするべきだということです。ご協力ありがとうございました。私はこれと格闘することから多くのことを学びました!

4

3 に答える 3

2

これを試してください:

mkfifo alt_in
(tail -f alt_in & rlwrap cat) | bash

プロンプトは表示されませんが、履歴の取得を含め、コマンドを入力したり、矢印キーなどを使用したりできます。別の端末から名前付きパイプにコマンドを送信できechoます。コマンドは受信側で実行されますが、履歴には残りません。

その他の調査事項:

  • 予想
  • screen -x および screen -X

後者の場合、1 つのターミナルで start を実行しscreenます。そこでは、通常どおり Bash を操作できます。別の端末で、

screen -ls

screen開始したセッションの PID を特定します。次のような行頭の数字になります。

31544.pts-2.hostname     (01/01/2010 01:01:01 PM)        (Attached)

これで、次のようなことができます。

screen -S 31544 -X stuff $'echo Your ad here.\n'

これにより、echoコマンドが他の端末で実行されます。内の$''エスケープ シーケンスが解釈されます。この場合、「押す」ことができるように改行が与えられますEnter

これを行ったとしましょう:

screen -S 31544 -X stuff $'top\n'

現在top実行中です。その端末に行って を押しqて終了することもできますが、それのどこが楽しいのでしょうか?

screen -S 31544 -X stuff 'q'

今回は改行が必要ないことに注意してください。

于 2010-11-25T07:19:56.083 に答える
1

をbashするためにデータをパイプしてみてくださいunbuffer

于 2010-11-25T06:23:08.357 に答える
0

キーボード入力には、「raw モード」、「cbreak モード」、「cooked モード」と呼ばれるさまざまな種類があります。

Raw モードでは、入力したすべてのキーストロークが OS からプログラム (たとえば、bash) に渡されます。

クック モードでは、OS が行をバッファリングし、文字の削除などの簡単な編集を行うことができます。RETURN または EOF (通常はCtrl-D) を押すと、プログラムに行が送信されます。

stty コマンドを使用すると、行末 (RETURN)、EOF (Ctrl-D) などとして解釈される多数のキーコードを定義できます。

Cbreak-mode は、制御文字の多くが通常の機能を保持しているが、OS が一度に 1 つずつ文字をアプリケーションに送信する中途半端な家です。通常、bash、vi、less などのプログラムは、このモードを使用します。

端末を raw モードに設定すると、実行中のプログラムが連携しない限り、キーボードを使用して端末から「抜け出す」ことができなくなります。

Expect ( hereまたはhere ) は、Bash に端末インターフェイスを提示できるため、通常のキーボードから実行されていると認識し、慣れ親しんだすべてのクールな bash コマンドライン編集を引き続き実行します。

また、Expect は raw モードのキーボードとパイプから入力を読み取り、シームレスに渡すことができます。

于 2010-11-25T07:18:58.263 に答える