OSX bash和期望

Joh*_*ver 5 bash

我有一个脚本,必须在多个主机上的每个主机上执行“ sudo”操作。我试图使工作正常,所以我只需要输入一次,就遇到了一些问题。

首先,建议使用几个示例:

/usr/bin/expect <<EOD
spawn ssh -t $host /usr/bin/sudo -v
expect "Password:"
send "$SUDOPASS\n"
EOD
Run Code Online (Sandbox Code Playgroud)

但是,一旦我输入第二个“ <”,所有的引用就搞砸了,我的脚本将以意外的文件结尾终止。这真的很奇怪,因为我对cat使用了相同的机制,以用其他脚本写出文件。

其他示例表明:

/usr/bin/expect -c "
spawn ssh -t $host /usr/bin/sudo -v
expect "Password:"
send "$SUDOPASS\n"
"
Run Code Online (Sandbox Code Playgroud)

以这种方式进行操作(并在期望值上加上-d),我得到的错误是:没有tty并重复输入密码,并在密码末尾附加了“ n”,因此它没有发送换行符(我已经尝试过'\ r”),但似乎转义了“ n”

由于我发现的大多数示例都来自Linux,因此我希望(哈,哈,双关语不是故意的!)他们使用的是GNU期望,而我使用的是BSD期望。我正在阅读手册页,但是“ spawn”一词出现了很多次,可能需要一段时间才能偶然发现正确的实例。

这似乎是最接近工作的结果:

flamingo:~ jnojr$ Scripts/getinfo_expect.sh 
Assuming you have one 'sudo' password for all of your hosts, enter it now: 
expect version 5.45
spawn /usr/bin/ssh -t macbook /usr/bin/sudo -v
parent: waiting for sync byte
parent: telling child to go ahead
parent: now unsynchronized from child
spawn: returns {67358}

expect: does "" (spawn_id exp7) match glob pattern "Password:"? no
Password:
expect: does "Password:" (spawn_id exp7) match glob pattern "Password:"? yes
expect: set expect_out(0,string) "Password:"
expect: set expect_out(spawn_id) "exp7"
expect: set expect_out(buffer) "Password:"
send: sending "password\n" to { exp7 }
argv[0] = /usr/bin/expect  argv[1] = -d  argv[2] = -c  argv[3] = 
    spawn /usr/bin/ssh -t macbook /usr/bin/sudo -v
    expect Password: { send password\n }  
set argc 0
set argv0 "/usr/bin/expect"
set argv ""
sudo: no tty present and no askpass program specified[/CODE]
Run Code Online (Sandbox Code Playgroud)

就是将'\ n'放在引号之外,例如

send "$SUDOPASS"\n
Run Code Online (Sandbox Code Playgroud)

除了跳过ssh的'-t'选项外,它似乎大部分都在工作

mor*_*ant 5

我第二个@BrianCain的评论说,无密码sshw / sudo是一个更好的解决方案。就是说,让我们尝试帮助您的expect脚本,您可以决定它是否仍然令人头疼。

我相信您会expect -f -在使用bash“此处字符串”(<<)将脚本输入到时使用(从STDIN读取脚本)expect。所以:

/usr/bin/expect -f - <<EOD
spawn ssh -t $host /usr/bin/sudo -v
expect "Password:"
send "$SUDOPASS\n"
EOD
Run Code Online (Sandbox Code Playgroud)