Java FTPClient 卡住
Java FTPClient Stuck
我正在尝试从我的 ftp 服务器下载文件,但在检索文件时卡住了。我正在使用 commons-net-3.6.jar
我注意到的事情
当我使用 ftpClient.enterRemotePassiveMode();
我可以在 FileZilla 服务器界面看到连接下载进度卡在 76%(688,128 字节)
当我使用 ftpClient.enterLocalPassiveMode();
我可以在 FileZilla 服务器界面看到连接下载进度卡在 96%(884,736 字节)
有趣的是,在这两种模式下,无论文件是什么,它总是卡在完全相同的字节数上。如果文件大小大于 884,736 或 688,128,它就会卡住。
对于 LocalPassiveMode 小于 884,736 字节和 RemotePassiveMode 小于 688,128 字节的文件,它非常适用。
我试过从不同的服务器下载但没有成功,所以这绝对不是服务器相关的问题。
我的代码
public class FTPDownload {
private List<BufferedImage> imageList;
private boolean wasConnected;
public void getFiles(String orderRootDirectory){
wasConnected = true;
imageList = new ArrayList<>();
FTPConnection con = new FTPConnection(); // to get the FTP Credentials
con.readData();
try {
FTPClient ftpClient = new FTPClient();
ftpClient.connect(con.getServerIp());
ftpClient.enterLocalPassiveMode();
ftpClient.login(con.getUsername(), con.getPassword());
ftpClient.setAutodetectUTF8(true);
ftpClient.setBufferSize(1024 * 1024); // tried with and without this no luck there
wasConnected = ftpClient.isConnected();
FTPFile[] files = ftpClient.listFiles(orderRootDirectory);
for (FTPFile file : files) {
String details = file.getName();
if (file.isDirectory()) {
details = "[" + details + "]";
}
String totalFilePath = orderRootDirectory+"/"+file.getName();
InputStream inputStream = ftpClient.retrieveFileStream(totalFilePath); // stuck over here
System.out.println(ftpClient.completePendingCommand());
System.out.println(ftpClient.getReplyString());
System.out.println("Reading File...");
long start=System.currentTimeMillis();
ImageIO.setUseCache(false);
BufferedImage bimg = ImageIO.read(inputStream);
long end=System.currentTimeMillis();
System.out.println("time="+(end-start));
imageList.add(bimg);
details += "\t\t" + file.getSize();
details += "\t\t" + file.getName();
System.out.println(details);
}
System.out.println(imageList.size());
ftpClient.logout();
ftpClient.disconnect();
}catch (Exception e){
e.printStackTrace();
wasConnected = false;
}
}
FTPClient#retrieveFileStream 表示:
You must close the InputStream when you finish reading from it. The
InputStream itself will take care of closing the parent data
connection socket upon being closed.
和
To finalize the file transfer you must call completePendingCommand and
check its return value to verify success. If this is not done,
subsequent commands may behave unexpectedly.
调用应该 finalized 使用 completePendingCommand
,现在你正在执行那个方法 before finalizing(你正在调用 completePendingCommand
后从 inputStream
读取。
此外,您没有关闭它明确指出的 inputStream
。
要解决您的问题,请执行以下操作,我们首先关闭 inputStream
,然后调用 completePendingCommand
,所有这些都应该在 之后发生已阅读 inputStream
.
InputStream inputStream = ftpClient.retrieveFileStream(totalFilePath);
BufferedImage bimg = ImageIO.read(inputStream);
inputStream.close();
if (!ftpClient.completePendingCommand()) {
// Throw some error or do something, file transfer failed
}
我正在尝试从我的 ftp 服务器下载文件,但在检索文件时卡住了。我正在使用 commons-net-3.6.jar
我注意到的事情
当我使用 ftpClient.enterRemotePassiveMode();
我可以在 FileZilla 服务器界面看到连接下载进度卡在 76%(688,128 字节)
当我使用 ftpClient.enterLocalPassiveMode();
我可以在 FileZilla 服务器界面看到连接下载进度卡在 96%(884,736 字节)
有趣的是,在这两种模式下,无论文件是什么,它总是卡在完全相同的字节数上。如果文件大小大于 884,736 或 688,128,它就会卡住。
对于 LocalPassiveMode 小于 884,736 字节和 RemotePassiveMode 小于 688,128 字节的文件,它非常适用。
我试过从不同的服务器下载但没有成功,所以这绝对不是服务器相关的问题。
我的代码
public class FTPDownload {
private List<BufferedImage> imageList;
private boolean wasConnected;
public void getFiles(String orderRootDirectory){
wasConnected = true;
imageList = new ArrayList<>();
FTPConnection con = new FTPConnection(); // to get the FTP Credentials
con.readData();
try {
FTPClient ftpClient = new FTPClient();
ftpClient.connect(con.getServerIp());
ftpClient.enterLocalPassiveMode();
ftpClient.login(con.getUsername(), con.getPassword());
ftpClient.setAutodetectUTF8(true);
ftpClient.setBufferSize(1024 * 1024); // tried with and without this no luck there
wasConnected = ftpClient.isConnected();
FTPFile[] files = ftpClient.listFiles(orderRootDirectory);
for (FTPFile file : files) {
String details = file.getName();
if (file.isDirectory()) {
details = "[" + details + "]";
}
String totalFilePath = orderRootDirectory+"/"+file.getName();
InputStream inputStream = ftpClient.retrieveFileStream(totalFilePath); // stuck over here
System.out.println(ftpClient.completePendingCommand());
System.out.println(ftpClient.getReplyString());
System.out.println("Reading File...");
long start=System.currentTimeMillis();
ImageIO.setUseCache(false);
BufferedImage bimg = ImageIO.read(inputStream);
long end=System.currentTimeMillis();
System.out.println("time="+(end-start));
imageList.add(bimg);
details += "\t\t" + file.getSize();
details += "\t\t" + file.getName();
System.out.println(details);
}
System.out.println(imageList.size());
ftpClient.logout();
ftpClient.disconnect();
}catch (Exception e){
e.printStackTrace();
wasConnected = false;
}
}
FTPClient#retrieveFileStream 表示:
You must close the InputStream when you finish reading from it. The InputStream itself will take care of closing the parent data connection socket upon being closed.
和
To finalize the file transfer you must call completePendingCommand and check its return value to verify success. If this is not done, subsequent commands may behave unexpectedly.
调用应该 finalized 使用 completePendingCommand
,现在你正在执行那个方法 before finalizing(你正在调用 completePendingCommand
后从 inputStream
读取。
此外,您没有关闭它明确指出的 inputStream
。
要解决您的问题,请执行以下操作,我们首先关闭 inputStream
,然后调用 completePendingCommand
,所有这些都应该在 之后发生已阅读 inputStream
.
InputStream inputStream = ftpClient.retrieveFileStream(totalFilePath);
BufferedImage bimg = ImageIO.read(inputStream);
inputStream.close();
if (!ftpClient.completePendingCommand()) {
// Throw some error or do something, file transfer failed
}