SSH 隧道作为本地服务的加密和身份验证

SSH 隧道作为本地服务的加密和身份验证

背景:

我的服务器上正在运行一个服务,该服务在域套接字上侦听/srv/socket传入连接,然后与连接的用户交互。请注意,此服务是我编写的(使用 C++),因此我可以非常轻松地修改服务的行为。现在,此服务不执行任何身份验证或权限检查(您稍后会看到这一点必须更改)。与我合作的几个开发人员(大约五到十个)需要从互联网上其他位置的计算机访问此服务(并且只能访问此服务)。由于此服务赋予他们相当多的权限,因此我希望身份验证尽可能强,并且连接是加密的。我的主要问题(为了避免任何 XY 问题)是:我该如何设置它?

关于它的想法和问题:

我最初的想法是提供自己的身份验证,然后使用 TLS 进行加密(当然,在外部端口上公开服务)。但是,编写自己的身份验证可能会导致安全漏洞,并且设置通过 TLS 进行连接会很麻烦。

我的第二个想法是只使用 SSH。SSH 已经具有非常强大的身份验证和加密功能,基本上可以满足我的需要。不幸的是,我不太清楚如何设置它。首先,我当然不想让开发人员拥有完全的 shell 访问权限,因此我将更改他们的默认 shell /bin/false(根据此网站和相关网站上的其他一些答案)。但我仍然需要他们能够连接到相关套接字。我研究了 ssh 隧道,但这似乎不是我需要的,其他类似于“ssh 作为代理”的搜索都揭示了相关但不完全相同的问题。这里正确的做法是什么?当然,我可以编写一个自定义可执行文件,它将充当“shell”,并简单地将这些用户连接到我的服务,但同样,此代码将具有安全性敏感性,在可能的情况下,我希望避免编写自己的代码。

最佳情况:

理想情况下,我希望发生以下情况:

  1. 用户在其客户端上运行一些命令。
  2. 创建到我的服务器上的代理服务的加密连接,并且用户向该服务进行身份验证(理想情况下,这是一个已知相当安全的完善的服务)。
  3. 代理服务打开与我的服务的连接,转发用户名(或某些用户标识符),然后连接客户端。

实现这一目标的最佳方法是什么?

答案1

我知道距离你提问已经有一段时间了,但如果你仍然感兴趣,可以看看我的邮政关于服务器故障。虽然那里的问题与您的要求无关,但我提出的解决方案可能直接相关。我希望从比我更了解安全影响的专家那里得到一些对该帖子的回应,但这并没有发生。

这篇文章有点长,不适合在这里重复,但简而言之,这个概念是:

  • 设置 SSH 以要求您需要/可以容忍的尽可能多的身份验证机制,例如密码 + 密钥 + otp 等。
  • 将用户 shell 设置为/sbin/nologin/sbin/nologin优先于/bin/false
  • 当用户通过 ssh 连接(验证)时,利用服务器上的 sshrc 调用脚本,该脚本可以执行您需要的任何操作,例如启动您的服务

在上述设置中,您的用户通过 SSH 进行身份验证,并且一旦通过身份验证,/etc/ssh/sshrc就对您的服务执行必要的操作,并/sbin/nologin在身份验证后正常断开 SSH 会话,因为不再需要它。

您可以随意使用 sshrc 中的脚本。例如,考虑从不为您的服务打开任何端口开始。一旦用户通过身份验证,sshrc 脚本就可以在您的防火墙中动态打开该用户 IP 的端口。

请注意:以上假设您确实非常清楚自己在 ssh 配置方面做了什么。虽然目前有几种经过良好测试的 SSH 实现,但其中许多很容易配置错误,从而带来重大安全隐患。此外,对于 SSH 身份验证,我强烈建议始终使用密钥 +(至少用户知道一件事,例如密码或 otp,最好两者兼有)。

相关内容