-
Spring Boot 시리즈 12편 – 파일 업로드 처리 전략: 이미지, 문서 업로드부터 S3 연동까지기술과 산업/언어 및 프레임워크 2025. 4. 26. 00:01728x90
Spring Boot에서 파일 업로드를 처리하는 전략을 소개합니다. 로컬 저장, 멀티파트 파일 처리, AWS S3 연동까지 실전 예제와 보안 고려사항을 함께 제공합니다.
Spring Boot 시리즈 12편 – 파일 업로드 처리 전략: 이미지, 문서 업로드부터 S3 연동까지
사용자 프로필 이미지, 게시글 첨부 파일, 문서 스캔 등
웹 서비스에서 파일 업로드는 거의 모든 도메인에서 요구되는 기능입니다.
이번 글에서는 Spring Boot에서 파일을 안전하게 업로드하고 저장하는 방법을,
- 로컬 파일 시스템 기반
- AWS S3 같은 외부 저장소 기반
- 으로 나누어 설계 → 구현 → 보안 → 유지보수 전략까지 통합적으로 다루어보겠습니다.
📌 1. 파일 업로드 처리 방식
방식설명특징
로컬 저장 서버 디렉토리에 파일 저장 빠르고 설정 간단, 확장성 낮음 외부 저장소 (S3) 클라우드 스토리지에 저장 확장성 ↑, 보안 ↑, 유지보수 유리 DB 저장 DB에 BLOB로 저장 비추천, 속도↓, 트래픽↑
✅ 2. 멀티파트 파일 기본 처리
1️⃣ Controller 구성
@RestController @RequestMapping("/api/files") public class FileUploadController { @PostMapping("/upload") public ResponseEntity<ApiResponse<String>> upload(@RequestPart MultipartFile file) throws IOException { String fileName = file.getOriginalFilename(); String path = "/upload-dir/" + UUID.randomUUID() + "_" + fileName; file.transferTo(new File(path)); return ResponseEntity.ok(ApiResponse.success("파일 업로드 성공: " + path)); } }
기본 설정만으로도 Spring Boot는 MultipartFile을 자동 처리합니다.
2️⃣ application.yml 설정
spring: servlet: multipart: max-file-size: 10MB max-request-size: 20MB
- 업로드 용량 제한 설정 필수
- 대용량 파일 처리 시 파일 스트리밍 방식 고려 필요
🔐 3. 파일 저장 시 보안 고려사항
항목권장 설계
저장 경로 제한 외부 접근이 불가능한 서버 디렉토리 활용 확장자 제한 .exe, .sh 등 실행 파일 차단 파일명 변경 UUID 등으로 랜덤화 → 충돌 방지 파일 MIME 검사 file.getContentType()으로 서버단 확인 업로드 전 인증 반드시 로그인 사용자만 가능하도록 제한
☁️ 4. AWS S3 연동 파일 업로드
1️⃣ 의존성 추가 (Gradle)
implementation 'software.amazon.awssdk:s3:2.20.40'
2️⃣ S3Config 설정
@Configuration public class S3Config { @Value("${cloud.aws.s3.bucket}") private String bucket; @Bean public S3Client s3Client() { return S3Client.builder() .region(Region.AP_NORTHEAST_2) // 서울 리전 .credentialsProvider(ProfileCredentialsProvider.create()) .build(); } @Bean public String bucketName() { return bucket; } }
3️⃣ S3 업로드 서비스 구현
@Service @RequiredArgsConstructor public class S3FileService { private final S3Client s3Client; private final String bucketName; public String upload(MultipartFile file) throws IOException { String key = "uploads/" + UUID.randomUUID() + "_" + file.getOriginalFilename(); PutObjectRequest putRequest = PutObjectRequest.builder() .bucket(bucketName) .key(key) .acl(ObjectCannedACL.PUBLIC_READ) // 공개 여부 설정 .build(); s3Client.putObject(putRequest, RequestBody.fromInputStream(file.getInputStream(), file.getSize())); return s3Client.utilities().getUrl(builder -> builder.bucket(bucketName).key(key)).toExternalForm(); } }
4️⃣ Controller에서 호출
@PostMapping("/upload-s3") public ResponseEntity<ApiResponse<String>> uploadToS3(@RequestPart MultipartFile file) throws IOException { String fileUrl = s3FileService.upload(file); return ResponseEntity.ok(ApiResponse.success(fileUrl)); }
🧠 실무 설계 팁
항목전략
고속 업로드 클라이언트에서 S3 Pre-signed URL 방식 활용 (권장) 삭제 처리 API → key → S3 delete 호출 필요 썸네일 생성 이미지 업로드 시 썸네일 서비스 별도 구성 가능 DB 저장 실제 파일은 URL만 저장 (S3 key 또는 full URL) 파일 그룹화 사용자별 prefix (user/123/avatar.png) 관리로 정리
✅ 마무리 요약
항목요약
기본 처리 MultipartFile → file.transferTo() 용량 제한 application.yml로 설정 로컬 저장 vs S3 빠른 개발 vs 확장성, 보안, 유지보수성 보안 고려 확장자 제한, 인증 체크, 경로 보호 실무 연동 AWS SDK 기반 파일 업로드, URL 생성 및 공개 처리
📌 다음 편 예고
Spring Boot 시리즈 13편: 스케줄러와 배치 처리 전략 – Spring Task와 Quartz로 구현하는 실무 배치 구조
728x90'기술과 산업 > 언어 및 프레임워크' 카테고리의 다른 글