Ответ 1
Это не работает, потому что режим передачи по умолчанию для FTPClient - FTP.ASCII_FILE_TYPE
. Вам просто нужно обновить конфигурацию для передачи в двоичном режиме.
Я пытаюсь сделать ОЧЕНЬ простую загрузку файла. Я хочу, чтобы Java FTPClient мог загрузить любой файл, о котором я ему рассказываю. Но в pdf всегда все испортилось, и мой редактор pdf (Adobe) не откроет его, заявив, что есть ошибка ввода-вывода.
Я использую следующий класс:
import org.apache.commons.net.ftp.FTPClient;
....
FTPClient client = new FTPClient();
FileInputStream fis = null;
try {
client.connect("mydomain.com");
client.login("user", "password");
String filename = "myPDF.pdf";
fis = new FileInputStream(filename);
client.storeFile("temp.pdf", fis);
fis.close();
client.logout();
} catch (IOException e) {
e.printStackTrace();
}
Почему это не работает, и как его исправить?
Это не работает, потому что режим передачи по умолчанию для FTPClient - FTP.ASCII_FILE_TYPE
. Вам просто нужно обновить конфигурацию для передачи в двоичном режиме.
Добавьте это в свой файл
ftp.setFileType(FTP.BINARY_FILE_TYPE, FTP.BINARY_FILE_TYPE);
ftp.setFileTransferMode(FTP.BINARY_FILE_TYPE);
У меня была такая же проблема с файлами xlsx, и это было хорошим решением.
Часто забывается, что FTP имеет два режима работы: один для текстовых файлов, а другой для двоичных (изображений) файлов. В старые добрые времена, подключившись из ftp-клиента командной строки, мы тщательно запомнили, чтобы установить режим передачи перед запросом файла - или мы столкнулись с такой проблемой, с которой вы, похоже, сталкиваетесь. Сегодня многие ситуации, по-видимому, по умолчанию не являются бинарными, но не кажутся вашими.
Вероятно, вам нужно передать вашу реализацию ftp для передачи в режиме двоичного/изображения.
Попробуйте использовать BufferedInputStream, это пример рабочего кода:
BufferedInputStream bis = new BufferedInputStream(new FileInputStream(f));
res = client.storeFile("File Name", bis);
bis.close();
client.logout();
Из документация
Этот метод НЕ закрывает данный InputStream.
Итак, закройте FileInputStream перед вызовом logout()
Попробуйте это.
objFtpClient.setFileType(FTP.BINARY_FILE_TYPE);
objFtpClient.setFileTransferMode(FTP.BINARY_FILE_TYPE);
objFtpClient.enterLocalPassiveMode();
Для меня работало только ftp.setFileType(FTP.BINARY_FILE_TYPE, FTP.BINARY_FILE_TYPE), а когда я использовал ftp.setFileTransferMode(FTP.BINARY_FILE_TYPE), файл искажался.
Это выглядит как ошибка в библиотеке Commons NET, которая затронула версию 3.0. Попробуйте новую версию (3.0.1), которая исправила ошибку.