SSHFS:通过 SSH 超级轻松的文件访问
像 scp、sftp 和 rsync 这样的工具允许我们在这些帐户之间轻松安全地复制文件。但是,如果我们不想在使用文件之前将文件复制到本地系统,该怎么办?通常,这将是传统网络文件系统(如 NFS、OpenAFS 或 Samba)的用武之地。不幸的是,设置这些网络文件系统需要在两个系统上都具有管理员权限。
幸运的是,只要您具有 SSH 访问权限,就可以使用 SSHFS 挂载和使用远程目录树,就像它们是本地目录一样。SSHFS 在远程端不需要任何特殊软件,只需要一个支持 SFTP 扩展的现代 SSH 服务器。所有现代 Linux 发行版都支持此扩展,该扩展已添加到 2000 年 11 月发布的 OpenSSH 2.3.0 版本中。
SSHFS 构建于 FUSE 用户空间文件系统框架项目之上。FUSE 允许用户空间软件(在本例中为 SSH)向用户呈现虚拟文件系统接口。这类似于 /proc 和 /sys 文件系统如何以目录树中文件的形式呈现内核内部信息。SSHFS 连接到远程系统,并执行所有必要的操作,以提供远程文件的常规文件系统接口的外观和感觉。
我在将要挂载远程目录的工作站上使用 Fedora Core 4。远程系统也是 Fedora Core 4,但是任何运行带有 SFTP 扩展的现代 SSH 服务器的 *NIX 系统都可以工作。您的 Linux 内核还必须启用用户空间文件系统功能,无论是内置的还是作为模块。
SSHFS 所需的所有软件都可以作为可使用 yum 为 Fedora Core 4 安装的软件包获得。只需运行
$ yum install fuse-sshfs
这将自动安装 SSHFS、FUSE 和 fuse-lib 依赖项。您也可以从源代码构建 SSHFS,但稍后会详细介绍。
在您可以以非 root 用户身份使用 SSHFS 或任何其他基于 FUSE 的文件系统之前,您必须首先将这些用户添加到 fuse 组。在我的例子中,我的用户名是 matt。这可以从命令行以 root 身份使用以下命令完成
$ usermod -a -G fuse matt
fuse 组允许您限制哪些用户可以使用基于 FUSE 的文件系统。这很重要,因为 FUSE 安装了 setuid 程序,这始终带有安全隐患。在高度安全的系统上,应该评估和控制对此类程序的访问。
安装和配置软件后,我们就可以试用了。为了演示基本功能,我将连接到名为 my.randombox.com 的远程系统。SSHFS 的默认操作是挂载远程用户的 home 目录;这是 SSHFS 最常见的用途。就像挂载任何其他文件系统一样,您需要一个名为挂载点的空目录,远程文件系统将挂载在该目录下。我创建了一个名为 randombox_home 的挂载点,然后调用 sshfs 命令来挂载远程文件系统。以下是操作方法
$ cd $HOME $ mkdir randombox_home $ sshfs matt@my.randombox.com: randombox_home matt@my.randombox.com's password: ************ $ ls -l randombox_home/ -rw-r----- 1 matt users 7286 Feb 11 08:59 sshfs.article.main.txt drwx------ 1 matt users 2048 Mar 21 2001 projects drwx------ 1 matt users 2048 Dec 1 2000 Mail drwxr-xr-x 1 matt users 4096 Jun 8 2002 public_html $ cp ~/my_web_site/index.html randombox_home/public_html/
就这样。我在 my.randombox.com 上的 home 目录现在已挂载到本地工作站上的 randombox_home 目录下。在后台,FUSE、SSHFS 和远程 SSH 服务器正在完成所有繁重的工作,以使我的远程 home 目录看起来像任何其他本地文件系统一样。如果您想挂载 home 目录以外的目录,只需将其放在 sshfs 命令行上的冒号之后。您甚至可以指定 / 来挂载整个远程系统。当然,您只能访问远程用户帐户具有权限的文件和目录。其他所有内容都将收到“权限被拒绝”消息。下面显示了一个示例
$ cd $HOME $ mkdir randombox_slash $ sshfs matt@my.randombox.com:/ randombox_slash matt@my.randombox.com's password: $ ls -l randombox_slash/ total 0 drwxr-xr-x 1 root root 4096 Nov 15 10:51 bin drwxr-xr-x 1 root root 1024 Nov 16 07:11 boot drwxr-xr-x 1 root root 118784 Jan 26 08:35 dev drwxr-xr-x 1 root root 4096 Feb 17 10:37 etc drwxr-xr-x 1 root root 4096 Nov 29 09:30 home drwxr-xr-x 1 root root 4096 Jan 24 2003 initrd drwxr-xr-x 1 root root 4096 Nov 15 10:53 lib drwx------ 1 root root 16384 Nov 11 10:21 lost+found drwxr-xr-x 1 root root 4096 Nov 11 10:38 mnt drwxr-xr-x 1 root root 4096 Jan 24 2003 opt dr-xr-xr-x 1 root root 0 Jan 26 08:11 proc drwx------ 1 root root 4096 Mar 3 09:34 root drwxr-xr-x 1 root root 8192 Nov 15 13:50 sbin drwxrwxrwt 1 root root 4096 Mar 5 18:41 tmp drwxr-xr-x 1 root root 4096 Nov 11 10:55 usr drwxr-xr-x 1 root root 4096 Jan 20 08:16 var $ cat randombox_slash/etc/shadow cat: randombox_slash/etc/shadow: Permission denied $ ls -l randombox_slash/root/ ls: reading directory randombox_slash/root/: Permission denied total 0 $ ls -l randombox_slash/home/matt/ -rw-r----- 1 matt users 7286 Feb 11 08:59 sshfs.article.main.txt drwx------ 1 matt users 2048 Mar 21 2001 projects drwx------ 1 matt users 2048 Dec 1 2000 Mail drwxr-xr-x 1 matt users 4096 Jun 8 2002 public_html $
从上面的示例中可以看出,我需要输入密码才能完成与远程系统的 SSH 连接。这可以通过在本地和远程用户帐户之间创建信任关系来消除。这并非在所有情况下都适用,因为它本质上使帐户从安全角度来看是等效的。一个帐户上的任何恶意活动都可能通过信任传播到其他系统,因此请谨慎并充分了解设置信任关系的含义。要开始设置此功能,您需要创建一个 SSH 密钥对,其中包括分别名为 id_rsa 和 id_rsa.pub 的公钥和私钥文件。
公钥被复制到远程系统并放置在 $HOME/.ssh/authorized_keys 文件中。某些系统可能除了 authorized_keys 之外或代替 authorized_keys 使用文件名 authorized_keys2。
这允许任何拥有私钥的用户在没有密码的情况下进行身份验证。我们使用以下命令创建密钥对ssh-keygen。文件会自动放置在本地系统上的 $HOME/.ssh 目录中的正确位置。由于我们已经挂载了我的远程 home 目录,因此将公钥附加到 authorized_keys 文件非常容易。以下是所需的所有步骤(假设您创建了等效于 randombox_home 目录并将其挂载)
$ cd $HOME $ ssh-keygen -t rsa Generating public/private rsa key pair. Enter file in which to save the key (/home/matt/.ssh/id_rsa): <ENTER> Enter passphrase (empty for no passphrase): <ENTER> Enter same passphrase again: <ENTER> Your identification has been saved in /home/matt/.ssh/id_rsa. Your public key has been saved in /home/matt/.ssh/id_rsa.pub. The key fingerprint is: fa:e7:7c:e1:cb:7b:66:8b:67:07:05:99:7f:05:b9:4a matt@myworkstation $ mkdir randombox_home/.ssh $ chmod 700 randombox_home/.ssh $ cat .ssh/id_rsa.pub >> randombox_home/.ssh/authorized_keys $ chmod 600 randombox_home/.ssh/authorized_keys
在上面的示例中,我们使用空密码短语创建密钥对,然后将公钥附加到远程 home 目录中的 authorized_keys 文件,并设置权限。完成此操作后,我不再需要在连接到远程帐户时键入密码。为了测试这一点,我们首先使用以下命令卸载远程 home 目录
$ fusermount -u randombox_home
为了测试信任关系,我们可以尝试在远程系统上运行 uptime 命令
$ ssh matt@my.randombox.com uptime 12:20:40 up 38 days, 4:12, 0 users, load average: 0.11, 0.04, 0.01
很好,不需要密码。信任关系工作正常。如果您在使此信任关系工作方面遇到问题,请检查两个系统上 .ssh 中文件的权限。很多时候,宽松的权限会阻止 SSH 使用密钥文件。此外,请查看 syslog 日志文件。OpenSSH 的 sshd 服务器将消息记录到 syslog 中,这通常有助于诊断密钥文件问题。您可能需要在 sshd_config 文件(通常位于 /etc/ssh/ 中)中提高日志记录详细程度。
您还可以通过在上面的示例中运行带有 -vvv 选项的 ssh 来调试连接以提高详细程度。现在,让我们再次挂载远程目录。这次它不会提示我输入密码
$ cd $HOME $ mkdir randombox_home $ sshfs matt@my.randombox.com: randombox_home $ ls -l randombox_home/ -rw-r----- 1 matt users 7286 Feb 11 10:33 sshfs.article.main.txt drwx------ 1 matt users 2048 Mar 21 2001 projects drwx------ 1 matt users 2048 Dec 1 2000 Mail drwxr-xr-x 1 matt users 4096 Jun 8 2002 public_html
在最后一个示例中,我们配置并自动化了远程目录的非交互式挂载。由于我们不再被提示输入密码,我们可以将 SSHFS 挂载集成到脚本中,或者更好的是集成到 GNOME 桌面中。要配置 GNOME 自动挂载我们的远程 home 目录,我们将 SSHFS 挂载命令配置为会话启动程序。这是在“会话首选项”对话框中完成的。导航到“桌面”→“首选项”→“更多首选项”→“会话”->“添加”,然后如图 1 所示填写对话框。
下次登录时,GNOME 会自动为我挂载远程目录,如图 2 所示。
请注意,GNOME 在退出会话时并不可靠地终止此命令。您可以使用fusermount -u randombox_home命令手动卸载远程目录。另一种选择是通过修改 $HOME/.Xclients-default 文件来自动化卸载,以按如下方式运行 fusermount 命令
#!/bin/bash # (c) 2001 Red Hat, Inc. WM="gnome-session" WMPATH="/usr/bin /usr/X11R6/bin /usr/local/bin" # Kludged to run fusermount upon gnome logout. 20060301-MEH for p in $WMPATH ; do [ -x $p/$WM ] && $p/$WM; fusermount -u randombox_home; exit 0 done exit 1
请注意,每次运行 switchdesk 实用程序时,.Xclients-default 文件都会被重写。每次使用 switchdesk 实用程序更改默认桌面窗口管理器时,都必须修改此文件。
最后,您可以将适当的 sshfs 命令添加到适合您的发行版的启动文件中。这样,您的系统将在每次启动桌面时自动挂载所有 SSHFS 目录。
如果您的特定 Linux 发行版未预先打包 SSHFS,或者您只是想从源代码构建它,这也非常容易。首先,确认您已安装内核模块开发所需的任何文件或软件包。您需要这些来构建 FUSE 内核模块。然后,从 SourceForge 下载 FUSE 和 SSHFS 的最新源代码 tarball(请参阅在线资源)。将下载的 tarball 文件放在临时目录中,然后在该目录中使用以下命令构建和安装
$ tar -xzf fuse-2.5.2.tar.gz $ cd fuse-2.5.2 $ ./configure --prefix=/usr $ make $ su -c "make install" $ cd .. $ tar -xzf sshfs-fuse-1.5.tar.gz $ cd sshfs-fuse-1.5 $ ./configure --prefix=/usr $ make $ su -c "make install"
安装完所有内容后,您就可以执行之前介绍的任何示例了。安装后,sshfs 和 fusermount 命令将安装在 /usr/bin 中。
SSHFS 和 FUSE 允许挂载和使用任何远程存储,就像任何其他文件系统一样。如果您可以使用 SSH 登录,您就拥有所需的所有访问权限。
正如我之前所说,FUSE 是一个用于创建用户空间文件系统的框架。SSHFS 只是冰山一角。还有基于 FUSE 的文件系统可以透明地加密您的文件 (EncFS)、浏览蓝牙设备 (BTFS) 或将 CVS 存储库挂载为文件系统 (CvsFS)。也许您想知道如何处理 Gmail 帐户中的所有可用空间?好吧,GmailFS 允许您挂载您的 Gmail 帐户并像本地文件系统一样使用它。请参阅 FUSE 网站以获取这些和更多精彩项目,或者您可能想编写自己的项目。FUSE 具有 Perl、Python、TCL、C、C#、Ruby 和其他语言的语言绑定。
本文的资源: /article/8943。
Matthew E. Hoskins 是新泽西理工学院的高级 UNIX 系统管理员,他在那里维护许多公司管理系统。他喜欢尝试使各种不同的系统和软件协同工作,通常使用薄薄的一层 Perl(在本地称为“MattGlue”)。不编写系统时,他经常可以在厨房里找到黑客技术。Matt 是专业记者协会的成员。他渴望听到您的反馈,可以通过 matt@njit.edu 与他联系。