Feat: Presigned로 이미지 처리 추가 - S11P21S002-249

This commit is contained in:
kimtaesoo7 2024-10-02 13:32:47 +09:00
parent 3386a28758
commit 423b9977e1
3 changed files with 53 additions and 3 deletions

View File

@ -61,8 +61,7 @@ public class ImageController {
@PathVariable("project_id") final Integer projectId,
@PathVariable("folder_id") final Integer folderId) {
log.debug("requestImageList {}", imageMetaList);
// TODO: 변경
return imageMetaList.stream().map(o -> ImagePresignedUrlResponse.of(o.getId(), o.getFileName())).toList();
return imageService.uploadFolderByPresignedImage(memberId, imageMetaList, projectId, folderId);
}
@GetMapping("/folders/{folder_id}/images/{image_id}")

View File

@ -38,6 +38,7 @@ import java.time.format.DateTimeFormatter;
import java.util.ArrayList;
import java.util.Comparator;
import java.util.List;
import java.util.UUID;
import java.util.concurrent.CompletableFuture;
import java.util.stream.Stream;
@ -318,7 +319,38 @@ public class ImageService {
}
}
@Transactional
@CheckPrivilege(PrivilegeType.EDITOR)
public List<ImagePresignedUrlResponse> uploadFolderByPresignedImage(final Integer memberId,
final List<ImageMetaRequest> imageMetaList,
final Integer projectId,
final Integer folderId) {
Folder folder = getOrCreateFolder(folderId, projectId);
List<ImagePresignedUrlResponse> presignedUrls = new ArrayList<>();
for (ImageMetaRequest meta : imageMetaList) {
// UUID 생성 이미지 Key 지정
String uuid = UUID.randomUUID().toString();
String fileName = meta.getFileName();
String extension = getExtension(fileName);
String s3Key = uuid + "." + extension;
// Presigned URL 생성
String presignedUrl = s3UploadService.generatePresignedUrl(s3Key);
// DB에 이미지 메타데이터 저장
Image image = Image.of(fileName, s3Key, extension, folder);
imageRepository.save(image);
// Presigned URL과 함께 응답 데이터 생성
ImagePresignedUrlResponse response = ImagePresignedUrlResponse.of(meta.getId(), presignedUrl);
presignedUrls.add(response);
}
return presignedUrls;
}
// 이미지 가져오면서 프로젝트 소속 여부를 확인
private Image getImageByIdAndFolderIdAndFolderProjectId(final Integer folderId, final Long imageId, final Integer projectId) {
return imageRepository.findByIdAndFolderIdAndFolderProjectId(imageId, folderId, projectId)
.orElseThrow(() -> new CustomException(ErrorCode.DATA_NOT_FOUND));

View File

@ -1,5 +1,6 @@
package com.worlabel.global.service;
import com.amazonaws.HttpMethod;
import com.amazonaws.services.s3.AmazonS3;
import com.amazonaws.services.s3.model.*;
import com.amazonaws.util.IOUtils;
@ -19,6 +20,7 @@ import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLDecoder;
import java.nio.charset.StandardCharsets;
import java.util.Date;
import java.util.UUID;
import java.util.concurrent.CompletableFuture;
@ -68,7 +70,7 @@ public class S3UploadService {
try (InputStream inputStream = file.getInputStream()) {
return uploadImageToS3(inputStream, extension, projectId);
} catch (IOException e) {
log.debug("MultipartFile 업로드 에러 발생 {}",file.getOriginalFilename(), e);
log.debug("MultipartFile 업로드 에러 발생 {}", file.getOriginalFilename(), e);
throw new CustomException(ErrorCode.FAIL_TO_CREATE_FILE);
}
}
@ -152,4 +154,21 @@ public class S3UploadService {
throw new CustomException(ErrorCode.INVALID_FILE_PATH);
}
}
/**
* Presigned URL 생성
*/
public String generatePresignedUrl(String s3Key) {
Date expiration = new Date();
long expTimeMillis = expiration.getTime();
expTimeMillis += 1000 * 60 * 10; // 10분간 유효
expiration.setTime(expTimeMillis);
GeneratePresignedUrlRequest generatePresignedUrlRequest = new GeneratePresignedUrlRequest(bucket, s3Key)
.withMethod(HttpMethod.PUT) // PUT 방식
.withExpiration(expiration);
URL url = amazonS3.generatePresignedUrl(generatePresignedUrlRequest);
return url.toString();
}
}