启用S​​SH Shell访问,但禁用SFTP访问


21

我一直在寻找这个问题的可行答案,并且大多数答案都包含有关为什么不这样做的建议。但是,这是场景,它是有必要的:

我有一个控制台应用程序,在每个用户的.profile中,有一个用于该应用程序的启动命令,在启动该应用程序的命令之后,直接有一个“退出”命令,该命令将其注销。我只希望他们能够通过其提供的界面访问此控制台应用程序。启动后,该应用程序向用户显示可以通过该应用程序访问的客户端列表,每个客户端都有自己的数据目录。授予用户访问他们仅需要访问的客户端的权限。

现在的问题是:如果我给用户SSH访问权限,他们也将能够使用SFTP客户端登录,这将使他们直接访问应用程序的数据目录,这是非常不希望的,因为这也将给他们访问他们不应该访问的数据目录。

当使用telnet / FTP组合时,这是一件很简单的事情,但是现在我想让用户可以从Internet上的任何地方进行访问,因此我一直无法找到一种方法将他们拒之门外。仍然允许他们访问可以在其中运行应用程序的Shell。


8
我忘记了细节,但是我认为SSH允许您限制用户登录时仅运行单个命令。如果进行此设置,他们将无法获得完全的Shell访问权限。这可能对您的用例有用。(毕竟,可以使用SSHFS模拟SFTP访问。仅禁用SFTP不会阻止中度确定的用户访问其用户帐户可以访问的任何文件。)
David Z

3
另外,您可能需要考虑“重塑”用户。对于备用数据访问,这似乎是一个设计问题
Dennis Nolte 2014年

2
使用.profile它听起来像是错误的解决方案。我相信使用备用Shell设置用户会更有意义。
kasperd 2014年

3
不要尝试使用.profile技巧来限制访问,因为绕过它很简单。(有关详细信息,请参阅我的答案)
Aleksi Torhamo 2014年

Answers:


22

编辑:

如果情况不太明显,则以下答案并非旨在作为一种防止具有Shell访问服务器权限的人使用SFTP 的安全方法。这只是解释如何从外部可见性禁用它的答案。有关用户级别安全性的讨论,请参见@cpast和@Aleksi Torhamo的答案。如果安全是您的重点,那么这个答案就不合适。如果简单的服务可见性是您的重点,那么这就是您的答案。

现在,我们继续原始答案:


注释掉sshd_config中的sftp支持(当然还要重启sshd):

#Subsystem sftp /usr/lib/openssh/sftp-server


1
有时线路可能是Subsystem sftp internal-sftp
Kondybas 2014年

1
我有, Subsystem sftp /usr/libexec/sftp-server 但是那成功了。非常感谢
sosaisapunk 2014年

16
这听起来似乎不合理。如果可以在服务器上执行任意命令,则可以执行sftp服务器端程序。即使未安装,您也可以将其重新实现为长壳命令,并让sftp客户端发送该命令而不是sftp。这种方法可能会使使用sftp不太方便,但是无法阻止可以运行任意命令的用户使用这些命令进行文件传输。
R.,

1
@sosaisapunk这是不正确的。用户可以使用来运行他们想要的任何命令ssh user@host command,因为.profile如果这样做,则根本不会运行,因此您的应用程序将根本无法启动。他们可以通过简单地说来获得完全的shell访问权限ssh -t user@host bash。只需尝试一下,您就会看到。子系统只是命令别名。如果他们以前可以使用sftp,他们仍然可以使用它-以及他们想要的任何其他命令。请在下面阅读我的答案。
Aleksi Torhamo 2014年

1
@sosaisapunk:不,关键是您可以使用ssh来执行此操作,但不能这样做,.profile因为它并不意味着安全性,并且很容易被绕开。在我的回答中,我列出了三种使用ssh进行操作的方法。总之,就请将您的应用程序的调用.profile一个shell脚本,要么1)设定的shell脚本为用户的shell 2)设置相应的shell脚本(正确匹配)ForceCommandsshd_config3)切换到公共密钥验证并设置Shell脚本如command中所示.ssh/authorized_keys。(此外,您应该使用@name以便使人们收到有关评论的通知)
Aleksi Torhamo 2015年

28

正如其他人提到的那样,禁用sftp还远远不够-具有不受限制的ssh访问权限的用户可以查看其帐户有权查看的任何文件,可以修改他们有权修改的任何内容,并且可以轻松地下载自己可以读取的任何内容机。阻止他们这样做的唯一方法是实际上限制他们的访问。.profile限制用户使用也不是理想的选择,因为这不是它的用途(编辑:正如Aleksi在他的回答中提到的那样,绕行实际上是微不足道的.profile;有关的.profile是它是为了方便,而不是安全性,所以不是旨在限制用户。使用为安全性而设计的事物(例如以下事物)来提供安全性)。

有两种基本方法可以执行此操作:您可以通过文件权限限制它们,或强制它们仅执行控制台应用程序。第二种方法更好:将应限制使用控制台应用程序的用户分配给一个组(例如customers);然后在sshd_config中添加以下行:

Match Group customers
ForceCommand /path/to/app

这样做是为了使该组中用户的所有连接都打开控制台应用程序;他们无法启动其他任何东西,包括sftp服务器工具。这也使他们无法对系统执行任何其他操作,并且与不同.profile,它使用SSH服务器本身.profileForceCommand这样做(将它们限制在shell中,还可以防止执行不涉及启动shell的其他操作)。也不同于.profile,这被设计为安全性;它专门用于抵制恶意用户逃避它。

(可能是劣等的)替代方案将涉及创建一个新用户来运行控制台应用程序。然后,您将数据目录限制为该用户,设置该用户拥有的控制台应用程序,并u+s在程序上进行设置。这是setuid位;这意味着运行控制台程序的某人在程序所有者的许可下这样做。这样,用户本身没有访问目录的权限,只能通过程序获取目录。但是,您可能应该只使用ForceCommand,因为这会将所有访问限制为“仅运行此程序”。


4
我想补充一点,ForceCommand这不会阻止SSH端口转发。
nyuszika7h 2014年

1
实际上,依靠.profile不仅仅是“不理想”。它很容易被绕过(有关详细信息,请参阅我的回答),因此不提供任何保护,仅提供错误的安全感。
Aleksi Torhamo 2014年

@AleksiTorhamo啊。我怀疑您可以绕过它,但不确定如何绕行(我通常怀疑不用于安全性的事物可以绕开)。感谢您提供详细信息!
cpast

15

不要尝试这样做,.profile因为它不提供任何安全性,并且完全没有限制!

这不要紧,你放什么.profile,因为你可以绕过它通过简单地发出指令到SSH命令行中运行,像这样:ssh user@host command。您仍然可以通过执行常规shell访问ssh -t user@host bash

如另一个答案中所述,禁用sftp子系统完全没有帮助。子系统本质上只是命令的别名,您仍然可以正常使用sftp sftp -s /path/to/sftp-executable user@host

就像cpast和一些评论者所说的那样,您应该使用适当的机制来限制访问。那是,

  • ForceCommandsshd_config
  • 使用密码登录,并command="...".ssh/authorized_keys
  • 将用户的外壳更改为限制用户操作的内容

笔记:

  • command="..." 仅适用于一个密钥,因此它不限制使用密码或另一密钥的用户的ssh登录
  • 您可能还想限制端口转发等。(我听说过端口转发,x11转发,代理转发和pty分配)
    • AllowTcpForwarding 等在 sshd_config
    • no-port-forwarding 等在 .ssh/authorized_keys
  • 如果您正在运行其他守护程序(例如FTP),则应验证它们是否不允许用户进入(某些守护程序根据用户的外壳程序做出此决定,因此,如果更改了它,则可能需要重新检查一下)
  • 您可以将用户的外壳程序更改为可以执行所需操作的脚本。它要么不带参数就运行,要么像script -c 'command-the-user-wanted-to-run'
  • 双方ForceCommandcommand="..."通过用户的shell运行命令,所以如果用户的shell设置为如他们不这样做的工作。/bin/false要么/sbin/nologin

免责声明:无论如何我都不是这方面的专家,所以尽管我可以说这.profile件事并不安全,但我不能保证我不知道的其他方法不会造成一些“陷阱”关于。据我所知,它们是安全的,但我不会是第一个在互联网上犯错误的人。


1
似乎至少对于in来说是ForceCommand强制的无密码登录,而之前已被绕过,这是由于服务器中的错误所致:它旨在保护免受恶意用户攻击,而绕过该用户的用户则被视为一个严重漏洞。在SSH服务器中(因此是优先解决方案)。正如您所指出的那样,它可以通过设计绕过:由于它不被视为安全功能,因此从Shell开发人员的角度来看,用户绕过它是完全可以的。command=authorized_keys.profile
cpast 2014年

1
@cpast:是的,我正在考虑是否存在更多功能,例如端口转发。我的意思是,如果您不知道ssh允许端口转发并且仅用于ForceCommand限制访问,并且拥有一个仅在本地侦听连接并且不执行身份验证的守护程序,则ssh用户仍然可以访问该守护程序。我列出的功能是例如。githosting解决方案通常会禁用,并且我在联机帮助页中没有看到任何其他的“看上去很邪恶”的解决方案,但是我也没有找到任何官方的“这就是您ForceCommand安全使用方式”的文档。
Aleksi Torhamo 2014年

诚然~/.profile,用户可以编辑它,但是对安全性没有帮助,但是您可以通过将cpast的技术引入来使其有意义/etc/profile吗?您可以检查UID以将其限制为正确的用户。
小鸡们2014年

1
@chicks:不,它有完全相同的问题。问题不在于该文件是用户可编辑的。问题在于两个文件都可以完全绕开。这些文件仅用于登录shell,如果您只说ssh user@host,但告诉ssh运行命令,即得到该登录shell 。ssh user@host command-您再也不会获得登录外壳,并且完全不会触碰文件。因此,您只需简单地给ssh一个额外的参数,就可以绕过别人试图对文件创建的任何限制。
Aleksi Torhamo 2014年

2
@chicks:另外,我刚刚意识到您指的是cpast。cpast的答案中的方法not use .profile,它使用sshd_config并且应该是安全的。他只提到.profile了您不应该使用的方法。
Aleksi Torhamo 2014年

1

可以全局和每个用户/组启用SSH并禁用SFTP。

我个人需要这样做,因为我想允许通过SSH访问某些git存储库,而且我想禁用不需要的系统。在这种情况下,不需要SFTP。

全球范围

您可以通过两种方法为所有用户禁用SFTP。

缺少的子系统

可以通过Subsystem关键字配置SSH使用的SFTP守护程序。从sshd_config(5)手册中:

Subsystem
        Configures an external subsystem (e.g. file transfer daemon).
        Arguments should be a subsystem name and a command (with optional
        arguments) to execute upon subsystem request.

        The command sftp-server(8) implements the “sftp” file transfer
        subsystem.

        Alternately the name “internal-sftp” implements an in-process
        “sftp” server.  This may simplify configurations using
        ChrootDirectory to force a different filesystem root on clients.

        By default no subsystems are defined.

最后一行建议不要为“ sftp”定义任何子系统就足够了。

虚假的谎言

您还可以通过将SSH使用的SFTP守护程序设置为不可用的方式来禁用SFTP。例如,将“ sftp”子系统配置为/bin/false

Subsystem sftp /bin/false

当某些东西尝试通过SFTP登录时,SSH守护程序将尝试生成“ sftp守护程序” /bin/false。该/bin/false程序只做一件事,那就是返回一个错误代码。SFTP连接尝试实际上被拒绝。

每个用户/组

也可以按用户,组或其他几个条件禁用SFTP。

如果您希望用户获得常规的shell提示,则此方法不起作用。这也没有意义,因为如果您具有Shell访问权限,则可以绕开大多数内容。 仅当您只想授予对特定程序的访问权限时,它才起作用。

匹配

要匹配一组用户,可以使用Match关键字配置SSH 。从sshd_config(5)手册中:

Match
        ...

        The arguments to Match are one or more criteria-pattern pairs or the
        single token All which matches all criteria.  The available criteria
        are User, Group, Host, LocalAddress, LocalPort, and Address.  The
        match patterns may consist of single entries or comma-separated
        lists and may use the wildcard and negation operators described in
        the PATTERNS section of ssh_config(5).

        ...

几个例子:

  • Match User eva 匹配“ eva”用户
  • Match User stephen,maria 匹配“斯蒂芬”和“玛丽亚”用户
  • Match Group wheel,adams,simpsons 与“ wheel”,“ adams”,“ simpsons”组匹配

如果需要更多信息,请在sshd_config(5)手册中进行加载。

强制命令

通常,通过SSH连接时,您会获得用户的登录Shell,但可以将SSH配置为强制执行特定命令。该命令对于任何SSH连接(包括SFTP)都是强制执行的,因此您可以选择强制执行所需的命令。

可以使用ForceCommand关键字配置强制命令。从 sshd_config(5)手册中:

ForceCommand
        Forces the execution of the command specified by ForceCommand,
        ignoring any command supplied by the client and ~/.ssh/rc if
        present.  The command is invoked by using the user's login shell
        with the -c option.  This applies to shell, command, or subsystem
        execution.  It is most useful inside a Match block.  The command
        originally supplied by the client is available in the
        SSH_ORIGINAL_COMMAND environment variable.  Specifying a command of
        “internal-sftp” will force the use of an in-process sftp server that
        requires no support files when used with ChrootDirectory.  The
        default is “none”.

因此,您可以强制使用想要使用的受限命令ForceCommand <your command>。例如:

Match User kim
        ForceCommand echo 'successful login man, congrats'

在我要授予git访问权限的情况下,我只需要用户有权访问git-shell。这是为我的git用户禁用SFTP的部分,以及一些安全选项:

Match Group git

        # have to do this instead of setting the login shell to `git-shell`,
        # to disable SFTP
        ForceCommand /usr/bin/git-shell -c "$SSH_ORIGINAL_COMMAND"

        # disable stuff we don't need
        AllowAgentForwarding no
        AllowTcpForwarding no
        AllowStreamLocalForwarding no
        PermitOpen none
        PermitTunnel no
        PermitTTY no
        X11Forwarding no

就我而言,我只想允许特定授权密钥的MySQL访问(不允许SFTP访问和SSH终端窗口)(即,不对sshd_config文件进行任何更改)。我设法通过以下〜/ .ssh / authorized_keys选项来实现特定的键:command =“ / usr / bin / echo'仅允许MySQL访问。'”,no-pty,no-X11-forwarding,permitopen =“ 127.0.0.1:3306”
Martin_ATS
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.