将密钥代码发送到OS X上的命令行程序

时间:2010-04-11 04:06:54

标签: bash macos scripting keypress keycode

我想制作一个启动程序然后发送键输入的脚本。在psuedo-script中:

#!/bin/bash
./program << (PRESS CONTROL-Z)

程序正在运行,所以如果脚本中有其他命令,除非控制-z终止程序,否则将无法访问它们。

这可能吗?从我发现的,我认为它可能需要密码,但我可能是错的。

4 个答案:

答案 0 :(得分:2)

我认为这可能是一个比“期望”更好的解决方案,因为它可以在原生bash脚本中执行,我有兴趣看看你的想法。

使用

`printf "character code here"` 

注意反引号

因此,例如我编写了一个控制远程gnu屏幕会话的脚本,以下行打开窗口2并发出ctrl-c键组合

ssh -t user@$host screen -p 2 -X stuff `printf "\003"`
  • -t选项模拟远程计算机上的终端输入
  • -p允许我们在屏幕会话中指定我们连接的窗口的名称或编号。
  • \ 003是字符代码0x03的bash格式

有关代码的完整参考,请参阅here

要查找某些键输入的代码,您可以使用

printf "%#x\n" "'X"
0x58
  • X是您想要找到
  • 代码的关键
  • 要查找非文字的代码,你可以使用ctrl-v(使bash将下一个键附加到命令行而不是解释它),然后键入键组合,所以如果我想找到ctrl-的键代码c我将删除X按ctrl-v然后按ctrl-c。

上面提到的ascii代码引用的最后一件事是将0x13列为回车符,但在屏幕手册中它们列出了0x15作为回车键代码,有人知道为什么吗?我在本地屏幕上进行了测试,当我按下输入0x13时,但是当通过ssh发送命令到远程屏幕时,0x13不起作用,但是0x15不起作用。

希望有所帮助

答案 1 :(得分:1)

您可能正在寻找expect(来自http://expect.nist.gov/)。这涉及伪ttys的复杂性,使得程序看起来脚本的输入(在这种情况下,expect程序)来自终端。

或者,您可以使用echocat并将其输出通过管道传输到程序中 - 这取决于程序。

答案 2 :(得分:0)

如果您只想让程序在后台启动,请执行

#!/bin/bash
./program&

答案 3 :(得分:0)

如果您打算介绍该程序,请使用:

./program &    # The & sends the command to the background
echo commands here are executed while program is in the background
…
wait           # Wait for the completion of background commands
echo commands here are executed after background program has completed

编辑:如果您打算停止程序(如ctrl-Z经常在* nix shell中执行),您可以向它发送STOP信号:

kill -STOP pid

要恢复执行,请发送CONT信号:

kill -CONT pid

在每个示例中,pid是程序的进程ID。如果您在脚本中启动它,则很容易使用变量$!,例如

./prog &
echo prog started in the background
pid_of_prog=$!
kill -STOP $pid_of_prog
echo prog stopped
kill -CONT $pid_of_prog
echo prog continues
wait
echo prog finished

编辑2:如果您的程序是在收到ctrl-Z字符时退出的程序,请记住控制字符具有字母表中位置字母的数值(即Ctrl- A是1,Ctrl-B是2,等等。要将此角色发送到某个程序,您可以:

echo -e "\032" | ./prog

032是26,即^ Z,八进制。当然,您可以通过任何方式生成相同的字符,也许可以将其添加到其他输入的末尾,如( cat inputfile ; echo -e "\032" ) | ./prog

但这可能不一定有效;程序必须设计为从输入中识别这个字符(它可能不会);通常贝壳抓住它。然后,大多数从stdin读取输入的程序只在输入结束时退出,因此重定向任何有限输入(甚至</dev/null)都会导致它终止。

最后,如果意图是在发生某些其他事件(在脚本中的其他位置检测到)时停止执行程序,则可以kill它......