bash - 如何使用脚本启动 ssh session 而不重定向 stdin?

标签 bash unix vim ssh expect

我有一系列 bash 命令,其中一些带有交互式提示,需要在远程计算机上运行。我必须针对不同的场景按一定的顺序调用它们,所以我一直在尝试制作一个 bash 脚本来为我自动化该过程。然而,似乎使用 bash 脚本启动 ssh session 的所有方法都会导致将 stdin 重定向到用于启动脚本的任何字符串或文件。第一名。

有没有一种方法可以指定在远程计算机上执行某个脚本,同时还可以通过 sshstdin 转发到本地计算机,以便用户能够与任何提示进行交互吗?

这是我必须澄清我想要做什么的要求列表。

  1. 在远程计算机上运行脚本。
  2. 在远程脚本中间的某个位置是提示输入的命令。示例:git commit 将调出 vim
    • 如果该命令是 git commit 并且它启动了 vim,则用户应该能够与 vim 进行交互,就好像它正在运行一样在他们的本地机器上。
    • 如果该命令提示输入[y/n]响应,用户应该能够输入他们的答案。
  3. 用户输入必要的信息后(通过退出 vim 或在提示符下按回车键),脚本应继续像正常一样运行。
  4. 然后我的脚本将终止 ssh session 。最终产品是为用户执行命令,而他们不需要知道它是通过远程连接执行的。

我一直在使用我想在远程计算机上运行的以下脚本测试各种不同的方法。

#!/bin/bash
echo hello
vim
echo goodbye
exit

用户能够使用 vim 至关重要,然后,当用户完成后,“再见”应该打印到屏幕上,并且远程 session 应该终止。

我尝试将临时脚本上传到远程计算机,然后运行 ​​ssh user@host bash/tmp/myScript,但这似乎也接管了 stdin完全无法让用户响应用户输入的提示。我尝试添加 -t-T 选项(我不确定它们是否不同),但我仍然得到相同的结果。

一位评论者提到使用 expectspawninteract,但我不确定如何一起使用这些工具来获得我的期望的行为。看起来 interact 会导致用户获得对 stdin 的控制权,但是一旦用户退出 vim 就无法放弃它为了让我的脚本继续执行。

我想要的行为可能吗?

最佳答案

好的,我想我已经找到我的问题了。我正在为 ssh 创建一个包装脚本,如下所示:

#!/bin/bash

tempScript="/tmp/myScript"
remote=user@host

commands=$(</dev/stdin)

cat <(echo "$commands") | ssh $remote "cat > $tempScript && chmod +x $tempScript" &&
ssh -t $remote $tempScript
errorCode=$?

ssh $remote << RM
  if [[ -f $tempScript ]]; then
    rm $tmpScript
  fi
RM

exit $errorCode

我在那里重定向了stdin,而不是ssh。当我提出问题时我应该提到这一点。我一遍又一遍地阅读该脚本,但我想我只是忽略了这一行。删除该行完全解决了我的问题。

只是为了澄清,将我的脚本更改为以下内容完全解决了我的问题。

#!/bin/bash

tempScript="/tmp/myScript"
remote=user@host

commands="$@"

cat <(echo "$commands") | ssh $remote "cat > $tempScript && chmod +x $tempScript" &&
ssh -t $remote $tempScript
errorCode=$?

ssh $remote << RM
  if [[ -f $tempScript ]]; then
    rm $tmpScript
  fi
RM

exit $errorCode

一旦我更改了包装脚本,问题中描述的测试脚本就起作用了!我能够在屏幕上打印“hello”,vim出现并且我能够像平常一样使用它,然后一旦我退出vim“goodbye”就被打印出来并ssh 客户端已关闭。

这个问题的评论者一直在为我指明正确的方向。很抱歉我只讲述了部分故事。

关于bash - 如何使用脚本启动 ssh session 而不重定向 stdin?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/37044129/

相关文章:

linux - bash 命令行参数到一个数组中,并根据参数值对数组进行子集化

bash - 如何创建和保存 bash 脚本

bash - 删除 Bash 脚本中的重复条目

oracle - Oracle中TNS_ADMIN变量有什么用?

vim - 制作时如何继续编辑文件?

bash - 为什么 bash 中的 $(( sum += i )) 告诉我 "command not found"?

python - 在 Unix 上安装 Python 设置工具以运行适用于 Python 的 Tweepy Twitter 客户端

linux - 专业人士可以做到 Bash + Escape

vim - 你能告诉 Vim 打开一个与命令行或 :e? 传递的文件不同的文件吗

macos - 如何在 macOS 中将 Caps Lock 映射到 Vim 的 Esc?