通过多跳的 SSH 隧道复制数据

Bar*_*man 16 linux ssh ssh-tunnel tunnel

我们有两个主要环境有问题:

开发和质量保证

每个环境有两台服务器:

  • 跳箱
  • 应用服务器

要连接应用服务器,必须先连接跳转盒,然后SSH连接应用服务器。

防火墙有一些规则:

  • 您必须通过跳转框连接到应用服务器
  • 应用服务器无法连接到任一跳箱
  • 跳转盒在同一个子网上,并且可以相互通信。

我们的问题

我们有很多的内容(670 GB) DEVELOPMENT APPLICATION SERVER,我们需要得到这个的QA APPLICATION SERVER

将此数据复制到跳转框不是一种选择,因为它们缺少所需的空间量。

我做了一些研究,并了解到我们可以通过这些服务器建立一系列隧道,以便我们可以通过隧道将数据直接从一个应用程序服务器传输到另一个应用程序服务器。但是,我们无法从应用服务器连接到跳转盒的问题。

我们有什么选择吗?这将是一个绝望的局面,时间至关重要。我们没有时间下载数据并重新上传。在服务器上通过网络进行复制会很快,因为它是千兆连接。

小智 17

到目前为止,最简单的方法是通过 scp 复制它。另外,这种语法实际上与其他一些建议不同。

您无法轻松击败这种语法。它允许您递归复制、rsync 或任何您想要的东西,而无需考虑潜在的复杂管道。这种语法直观清晰,将更容易被跟随您的系统管理员支持,并且不会无用地使用 cat

scp -3 devappserver:/path/to/copy/from qaappserver:/path/to/copy/to
Run Code Online (Sandbox Code Playgroud)

scp 手册页-3两个远程主机之间的副本通过本地主机传输。如果没有此选项,数据将直接在两个远程主机之间复制。请注意,此选项会禁用进度表。

在下面的例子中

  • 您的工作站名为 MacBook-Pro。
  • Dev Jump Box 被命名为 devjumpserver
  • Dev Application Server 被命名为 devapplicationserver
    • 位于名为 .local 的 LAN DNS 区域上
  • QA Jump Box 被命名为 qajumpserver
  • QA 应用服务器名为 qaapplicationserver
    • 位于名为 .local 的 LAN DNZ 区域上
  • 我们将执行 670GB /etc/hosts 文件的测试副本;-)
  • 假设您已配置 SSH 公钥身份验证。



这是一个 ~/.ssh/config 文件,它通过适当的跳转(又名堡垒服务器)设置从工作站到应用程序服务器的直接访问。

MacBook-Pro:~ barrychapman$ cat ~/.ssh/config
主持人 *
  ServerAliveInterval 60
主机开发应用服务器
  主机名 devapplicationserver.local
  ProxyCommand ssh -i ~/.ssh/id_rsa barrychapman@devjumpserver.example.com -W %h:%p
  用户 barrychapman
主机 qaapplicationserver
  主机名 qaapplicationserver.local
  ProxyCommand ssh -i ~/.ssh/id_rsa barrychapman@qajumpserver.example.com -W %h:%p
  用户 barrychapman

MacBook-Pro:~ barrychapman$



测试目标服务器上是否存在文件,它不会存在。

MacBook-Pro:~ barrychapman$ ssh qaapplicationserver ls /tmp/hosts
ls: 无法访问 /tmp/hosts: 没有那个文件或目录
被信号 1 杀死。
MacBook-Pro:~ barrychapman$



现在让我们通过您的工作站将文件从开发应用程序服务器复制到 QA 应用程序。

MacBook-Pro:~ barrychapman$ scp -3 devapplicationserver:/etc/hosts qaapplicationserver:/tmp/
被信号 1 杀死。
被信号 1 杀死。
MacBook-Pro:~ barrychapman$



现在让我们检查 QA 应用程序服务器上是否存在复制的文件。这次它会在那里。

MacBook-Pro:~ barrychapman$ ssh qaapplicationserver ls /tmp/hosts
/tmp/主机
被信号 1 杀死。
MacBook-Pro:~ barrychapman$ 

笔记

关闭 ProxyCommand 连接时,您将看到警告消息“被信号 1 杀死”。这是 SSH 拆除 ProxyCommand 连接,无需担心。您可以通过添加LogLevel Quiet到堡垒主机配置节来摆脱它。


vor*_*aq7 7

管道!

如果互联网是一系列管道,那么 Unix 就是一系列管道——例如:

cat ginormous-file | ssh user@host1 "cat | ssh user@host2 \"cat >out\" "
Run Code Online (Sandbox Code Playgroud)

应该管用。

如果您需要遍历更多主机,请根据需要添加更多管道(以及更多嵌套的\-escaped 引用层)。(但是请注意,如果管道/转义变得如此复杂以至于您必须绘制图表或依靠手指来确定您必须在转义上加倍次数,那么可能是时候承认失败并设置适当的 VPN !)

  • 正如 [Alex_www 在他的评论中指出的](http://serverfault.com/questions/560970/copy-data-through-ssh-tunnel-over-multiple-hops/560991#comment651108_560970) 如果你不需要*任何东西的中间文件,你也可以通过管道传递 `tar` 的输出。(同样在管道的中间阶段你不需要*`cat` - `ssh`很高兴吃stdin并传递它。`cat`只是让我感觉更好,并且是其他有用的占位符您可能想要使用的命令,例如`tee`。) (2认同)