背景
Java 程序访问第三方SFTP服务器下载文件,第三方只提供账号+私钥(key.ppk
文件)
引入工具包(jsch)
建议引用最新版本,一开始版本过低,报错了
<!-- https://mvnrepository.com/artifact/com.jcraft/jsch -->
<dependency>
<groupId>com.jcraft</groupId>
<artifactId>jsch</artifactId>
<version>0.1.54</version>
</dependency>
DEMO
package com.ctrip.ibu.yzy.test.ftp;
import com.jcraft.jsch.ChannelSftp;
import com.jcraft.jsch.JSch;
import com.jcraft.jsch.Session;
import java.util.Properties;
import java.util.Vector;
public class FTPTest {
public static void main(String[] args) {
JSch jsch = new JSch();
Session session = null;
ChannelSftp channel = null;
String path = FTPTest.class.getProtectionDomain().getCodeSource().getLocation().getPath();
try {
jsch.addIdentity(path + "key.ppk");
session = jsch.getSession("username", "host", 22);
Properties config = new Properties();
config.put("StrictHostKeyChecking", "no");
session.setConfig(config);
session.setTimeout(20000);
session.connect();
channel = (ChannelSftp) session.openChannel("sftp");
channel.connect();
Vector vector = channel.ls("/infiles/");
for (Object obj : vector) {
if (obj instanceof ChannelSftp.LsEntry) {
ChannelSftp.LsEntry entry = (ChannelSftp.LsEntry) obj;
System.out.println(entry.getFilename());
}
}
} catch (Exception e) {
e.printStackTrace();
} finally {
channel.quit();
session.disconnect();
}
}
}
控制台输出infiles
目录下所有 文件名
.
..
634_Hotel_report_20190521.csv.gz
634_Hotel_report_20190306.csv.gz
634_Hotel_report_20190412.csv.gz
634_POS_report_20190509.csv.gz
634_POS_report_20190512.csv.gz
634_Hotel_report_20190409.csv.gz
jsch 其他方法可以自行谷歌
踩坑
以上看起来没有什么问题,当我发布到测试环境(linux)的时候,运行报异常:
com.jcraft.jsch.JSchException: invalid privatekey: [B@392b0008
网上翻了好多帖子也没有找到解决方案,猜测是秘钥问题,果然看到有说mac系统无法使用ppk远程登录的帖子。
解决方案
下载Puttygen
,将key.ppk
转换成 key.pem
修改后的代码,测试通过
boolean windows = System.getProperty("os.name").toLowerCase().contains("windows");
String path = getClass().getClassLoader().getResource(windows ? "key.ppk" : "key.pem").getPath();
......