Piszę prosta przelotkę na FTPa, która pozwoli mi przez RESTa wrzucać zdjęcia. Kod wygląda dość prosto:
@RestController
@RequestMapping("/image")
@RequiredArgsConstructor
class ImageController {
private final QuestionImageService imageService;
@PostMapping("/upload")
ResponseEntity<ImageDto> uploadQuestionImage(@RequestParam MultipartFile file) {
return new ResponseEntity<>(imageService.uploadQuestionImage(file), HttpStatus.OK);
}
}
@Service
@RequiredArgsConstructor
public class QuestionImageService {
private static final String IMAGE_EXTENSION = ".png";
private static final String TEMP_IMAGE = "temp";
private static final String TEMP_DIRECTORY = "java.io.tmpdir";
private final FtpImageRepository repository;
public ImageDto uploadQuestionImage(MultipartFile multipartFile) {
try {
var id = repository.saveImage(multipartToFile(multipartFile), IMAGE_EXTENSION);
return new ImageDto(id);
} catch (IOException e) {
throw new RuntimeException(e);
}
}
private synchronized File multipartToFile(MultipartFile multipart) throws IllegalStateException, IOException {
File file = new File(System.getProperty(TEMP_DIRECTORY) + File.separator + TEMP_IMAGE + IMAGE_EXTENSION);
FileUtils.writeByteArrayToFile(file, multipart.getBytes());
return file;
}
}
@Repository
public class FtpImageRepository implements ImageRepository {
@Value("${ftp.server}")
private String server;
@Value("${ftp.port}")
private int port;
@Value("${ftp.user}")
private String user;
@Value("${ftp.password}")
private String password;
private FTPClient ftp;
@Override
public synchronized String saveImage(File file, String extension) {
var id = UUID.randomUUID().toString();
try {
open();
ftp.storeFile(id + extension, new FileInputStream(file));
close();
} catch (IOException e) {
throw new RuntimeException(e);
}
return id;
}
private void close() throws IOException {
ftp.disconnect();
}
private void open() throws IOException {
ftp = new FTPClient();
ftp.connect(server, port);
int reply = ftp.getReplyCode();
if (!FTPReply.isPositiveCompletion(reply)) {
ftp.disconnect();
throw new IOException("Exception in connecting to FTP Server");
}
ftp.login(user, password);
}
}
No i generalnie to działa, ale nie do końca... dla testów wziąłem przykładowy obrazek *.jpeg z googla. Wrzuciłem go przez postmana, sprawdzam przez WinSCP - jest, mogę pobrać i otworzyć. Wziąłem drugi rysunek, ale postanowiłem go najpierw w **paincie **zmniejszyć i zapisać w zarówno *.jpg jak i *.jpeg.
Wszystko się teoretycznie udaje, plik po pobraniu z FTPa nawet waży tyle samo, ma nadal poprawne rozszerzenie, ale gdy próbuje go otworzyć dostaje komunikat, że danego formatu nie da się otworzyć... Ktoś spotkał się z podobnym problemem?