先说我需要实现的功能
通过数据库查找到的图片名称的集合,去ftp服务端上根据查找到的图片名称下载对应的图片,保存
到本地的文件夹
再说我遇到的两个问题
1.关于更改ftp的工作目录
这个D:\ftp就是我的ftp的服务路径,该路径下的所有文件都可以被ftp访问。
我在下载文件之前,更改了工作目录,
将其设置为了ftp下的part目录 partftpClient.changeWorkingDirectory("/part/");
所以当工作目录切换了之后下面代码中retrieveFile()方法的第一个参数就填文件名即可
package com.wuqiang;
import org.apache.commons.net.ftp.FTP;
import org.apache.commons.net.ftp.FTPClient;
import org.apache.commons.net.ftp.FTPFile;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
public class FtpGetOne {
public static void main(String[] args) {
String server = "ftp地址";
int port = 21;
String user = "用户名";
String password = "密码";
//本地文件夹地址
String localDirPath = "D:\\Desktop\\data\\";
FTPClient ftpClient = new FTPClient();
try {
ftpClient.connect(server, port);
ftpClient.login(user, password);
ftpClient.enterLocalPassiveMode();
ftpClient.setFileType(FTP.BINARY_FILE_TYPE);
// 更改工作目录到part文件夹
boolean b1 = ftpClient.changeWorkingDirectory("/part/");
// 获取到part目录下的所有文件
FTPFile[] remoteFiles = ftpClient.listFiles();
for (FTPFile ftpFile : remoteFiles){
String fileName = ftpFile.getName();
String localFilePath = localDirPath+fileName;
FileOutputStream fos = new FileOutputStream(localFilePath);
//因为更改了工作目录,所以获取part文件夹下的图片时,retrieveFile()方法的第一个参数就填文件名即可
boolean success = ftpClient.retrieveFile(fileName, fos);
fos.close();
if (success) {
System.out.println("Image downloaded successfully.");
} else {
System.out.println("Image download failed.");
}
}
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
if (ftpClient.isConnected()) {
ftpClient.logout();
ftpClient.disconnect();
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
2.关于下载文件失败问题(获取到的文件名乱码)
上面这段代码,在执行到 FTPFile[] remoteFiles = ftpClient.listFiles();的时候打断点可以看到获取
到的文件名字全部是乱码的
这是ftp服务端跟ftp客户端的编码格式不一致导致的
因为一开始我也不知道到底是啥编码格式,于是我就找了一段乱码的去网上搜了一下乱码恢复
可以看到第二行的恢复结果是正确的,然后我们就知道了,ftp客户端那边是GBK编码,而现在显
示的是iso-8859-1编码格式。
于是我去把编码格式设置成了GBK,
ftpClient.setControlEncoding("GBK");
果然!文件名乱码这里就解决了,打断点查看确实没问题,没乱码了,但是!
接下来当程序执行到
ftpClient.retrieveFile(fileName, fos)
的时候,返回的值是false,然后我又去查看了本地文件夹中的这张图片,显示格式已损坏,查看一下文件属性,文件大小为零。很显然图片没有下载成功
1. 去ftp服务端看了一下有没有给当前登陆的用户授权
2. 能否ping通ftp的地址
3. 将ftp文件属性只读给取消勾勾(不知道有没有用)
4. 文件地址错误,我估计是编码格式的原因,没有读取到ftp上的文件
前面三种我都检查了一遍,我是出在文件地址错误,这也是我前面给自己埋下的坑。
前面因为中文乱码问题,于是我设置了编码格式为GBK
我们把ftpClient.setControlEncoding("GBK");注释掉
然后这个时候会发现文件名开始乱码了,不要慌,将for循环里面的代码修改一下,
然后再运行就下载成功了
for (FTPFile ftpFile : remoteFiles){
//定义一个GBK编码格式的文件名
String remoteFilePath = new String("111490-一轴轴承(导向轴承).jpg".getBytes("GBK"), "GBK");
//GBK转成iso-8859-1
String str = new String(remoteFilePath.getBytes("GBK"),"iso-8859-1");
String localFilePath = localDirPath+remoteFilePath;
FileOutputStream fos = new FileOutputStream(localFilePath);
boolean success = ftpClient.retrieveFile(str, fos);
fos.close();
if (success) {
System.out.println("Image downloaded successfully.");
} else {
System.out.println("Image download failed.");
}
}