Skip to content

Commit bb36609

Browse files
authored
Merge pull request #58 from POPCONG/develop
[deploy] S3 오류 확인 로그 추가
2 parents 2bb4220 + 92b61f2 commit bb36609

1 file changed

Lines changed: 72 additions & 57 deletions

File tree

Lines changed: 72 additions & 57 deletions
Original file line numberDiff line numberDiff line change
@@ -1,57 +1,72 @@
1-
//package popcong.app.adapter.out.image;
2-
//import com.amazonaws.auth.DefaultAWSCredentialsProviderChain;
3-
//import com.amazonaws.regions.Regions;
4-
//import com.amazonaws.services.s3.AmazonS3;
5-
//import com.amazonaws.services.s3.AmazonS3ClientBuilder;
6-
////import com.amazonaws.services.s3.model.ObjectMetadata;
7-
////import com.amazonaws.services.s3.model.PutObjectRequest;
8-
//import lombok.extern.slf4j.Slf4j;
9-
//import org.springframework.stereotype.Component;
10-
////import org.springframework.web.multipart.MultipartFile;
11-
//import popcong.app.application.image.port.out.ProfileImageUploadPort;
12-
////import popcong.app.global.exception.custom.BusinessException;
13-
//import popcong.app.global.exception.error.ImageS3ErrorCode;
14-
//
15-
//import java.io.IOException;
16-
//
17-
//
18-
//@Slf4j
19-
//@Component
20-
//public class S3ProfileImageUploadAdapter implements ProfileImageUploadPort {
21-
//
22-
// private final AmazonS3 s3;
23-
// private final String bucket = "popcongbucket";
24-
// private final Regions region = Regions.US_EAST_2; //오하이오
25-
//
26-
// public S3ProfileImageUploadAdapter() {
27-
// this.s3 = AmazonS3ClientBuilder.standard()
28-
// .withRegion(region)
29-
// .withCredentials(DefaultAWSCredentialsProviderChain.getInstance())
30-
// .build();
31-
// }
32-
33-
// @Override
34-
// public String uploadProfileImage(Long userId, MultipartFile file) {
35-
// try {
36-
// String key = buildKey(userId, file.getOriginalFilename());
37-
//
38-
// ObjectMetadata meta = new ObjectMetadata();
39-
// meta.setContentLength(file.getSize());
40-
// meta.setContentType(file.getContentType());
41-
//
42-
// PutObjectRequest req = new PutObjectRequest(bucket, key, file.getInputStream(), meta);
43-
// s3.putObject(req);
44-
//
45-
// return "https://%s.s3.%s.amazonaws.com/%s"
46-
// .formatted(bucket, region.getName(), key);
47-
//
48-
// } catch (IOException e) {
49-
// log.error("S3 업로드 실패", e);
50-
// throw new BusinessException(ImageS3ErrorCode.FILE_UPLOAD_ERROR);
51-
// }
52-
// }
53-
// private String buildKey(Long userId, String original) {
54-
// String safe = (original == null ? "unknown" : original).replaceAll("\\s+", "_");
55-
// return "profiles/%d/%d_%s".formatted(userId, System.currentTimeMillis(), safe);
56-
// }
57-
//}
1+
package popcong.app.adapter.out.image;
2+
import com.amazonaws.AmazonServiceException;
3+
import com.amazonaws.SdkClientException;
4+
import com.amazonaws.auth.DefaultAWSCredentialsProviderChain;
5+
import com.amazonaws.regions.Regions;
6+
import com.amazonaws.services.s3.AmazonS3;
7+
import com.amazonaws.services.s3.AmazonS3ClientBuilder;
8+
import com.amazonaws.services.s3.model.ObjectMetadata;
9+
import com.amazonaws.services.s3.model.PutObjectRequest;
10+
import lombok.extern.slf4j.Slf4j;
11+
import org.springframework.stereotype.Component;
12+
import org.springframework.web.multipart.MultipartFile;
13+
import popcong.app.application.image.port.out.ProfileImageUploadPort;
14+
import popcong.app.global.exception.custom.BusinessException;
15+
import popcong.app.global.exception.error.ImageS3ErrorCode;
16+
17+
import java.io.IOException;
18+
19+
20+
@Slf4j
21+
@Component
22+
public class S3ProfileImageUploadAdapter implements ProfileImageUploadPort {
23+
24+
private final AmazonS3 s3;
25+
private final String bucket = "popcongbucket";
26+
private final Regions region = Regions.US_EAST_2; //오하이오
27+
28+
public S3ProfileImageUploadAdapter() {
29+
this.s3 = AmazonS3ClientBuilder.standard()
30+
.withRegion(region)
31+
.withCredentials(DefaultAWSCredentialsProviderChain.getInstance())
32+
.build();
33+
}
34+
35+
@Override
36+
public String uploadProfileImage(Long userId, MultipartFile file) {
37+
String key = buildKey(userId, file.getOriginalFilename());
38+
39+
try {
40+
ObjectMetadata meta = new ObjectMetadata();
41+
meta.setContentLength(file.getSize());
42+
meta.setContentType(file.getContentType());
43+
44+
PutObjectRequest req = new PutObjectRequest(bucket, key, file.getInputStream(), meta);
45+
46+
// ✅ 예외 상세 로그 추가
47+
try {
48+
s3.putObject(req);
49+
return "https://%s.s3.%s.amazonaws.com/%s"
50+
.formatted(bucket, region.getName(), key);
51+
} catch (AmazonServiceException e) {
52+
// S3가 에러 응답을 보낸 경우 (권한, 리전 불일치 등)
53+
log.error("[S3 SERVICE] status={}, code={}, msg={}, bucket={}, key={}",
54+
e.getStatusCode(), e.getErrorCode(), e.getErrorMessage(), bucket, key, e);
55+
throw new BusinessException(ImageS3ErrorCode.FILE_UPLOAD_ERROR);
56+
} catch (SdkClientException e) {
57+
// 네트워크, 자격증명 문제
58+
log.error("[S3 CLIENT] msg={}, bucket={}, key={}", e.getMessage(), bucket, key, e);
59+
throw new BusinessException(ImageS3ErrorCode.FILE_UPLOAD_ERROR);
60+
}
61+
62+
} catch (IOException e) {
63+
log.error("[S3 IO] msg={}, bucket={}, key={}", e.getMessage(), bucket, key, e);
64+
throw new BusinessException(ImageS3ErrorCode.FILE_UPLOAD_ERROR);
65+
}
66+
}
67+
68+
private String buildKey(Long userId, String original) {
69+
String safe = (original == null ? "unknown" : original).replaceAll("\\s+", "_");
70+
return "profiles/%d/%d_%s".formatted(userId, System.currentTimeMillis(), safe);
71+
}
72+
}

0 commit comments

Comments
 (0)