当还必须切换用户时使用 JSch 到 SFTP

Using JSch to SFTP when one must also switch user

我在 Java 客户端中使用 JSch 连接到远程服务器并使用 SFTP 获取一些文件。以下代码对我来说工作正常:-

JSch ssh = new JSch();
JSch.setConfig(FileTransferConstants.STRICT_HOST_KEY_CHECKING, FileTransferConstants.NO);
Session session = ssh.getSession(userName, host, port);
session.setPassword(password);
session.connect();
Channel channel = session.openChannel(FileTransferConstants.SFTP);
channel.connect();
ChannelSftp sftp = (ChannelSftp) channel;
sftp.cd(remoteDirectoryPath);
sftp.lcd(localDirectoryPath);

sftp.get(remoteDirectoryPath + remoteFileName, remoteFileName);

问题是网站政策现在发生了变化。我不再被允许直接作为该用户(上面的用户名)登录。我必须首先以我的个人用户身份登录,然后 su 进入有权访问我想要 SFTP 的文件的用户。

我不认为我可以重构上面的代码来实现这个,所以我开始考虑使用 shell 或 exec 通道。到目前为止,我收效甚微,似乎无法在网上找到任何示例,所以我将非常感谢任何正确方向的建议或指示。非常感谢。

我不认为你可以直接用 JSch 来做这件事。但是通过对其代码进行一些修改,它可能是可行的。

请注意,我的回答假设服务器是基于 *nix 的(由您对 su 的引用支持)并使用 OpenSSH SFTP 服务器。


你必须打开 SSH "exec" 通道,才能执行如下命令:

sudo /bin/sftp-server

但在该频道之上,您需要构建 ChannelSftp 实例,而不是 ChannelExec

因此您需要实施类似 Session.openChannel 的方法,这将打开 exec 通道,但会为其创建 ChannelSftp


有关一些背景,请参阅 how it's possible to do sudo with WinSCP SFTP client

请注意,虽然 FAQ 声称您将无法为 sudo 使用密码,但对于 WinSCP 来说也是如此。但是由于您可以完全控制与 JSch 的会话,因此您可以将密码提供给 sudo.

为此,您可以覆盖 ChannelSftp.start() 以将密码写入通道输入,然后再开始实际的 SFTP 会话。

您仍然需要关闭 requiretty 选项,因为 SFTP 无法与 TTY 一​​起使用。


有关使用 different/root 帐户进行自动化操作时的一般注意事项,请参阅:
Allowing automatic command execution as root on Linux using SSH