스프링을 이용해 파일 업로드하는 방법에 대해 정리하고자 합니다.
스프링 코드와 html 코드를 작성하면서 설명하겠습니다.
Spring Code - 파일 업로드 처리
@Value("${file.path}")
private String fileRealPath;
public void imageUpload(ImageRequestDTO.ImageUploadDTO request, Long userId) throws IOException{
UUID uuid = UUID.randomUUID();
MultipartFile file = request.getFile();
String uuidFilename = uuid + "_" + file.getOriginalFilename();
Path filePath = Paths.get(fileRealPath + uuidFilename); // 파일의 저장 경로 설정
Files.write(filePath, file.getBytes()); // 하드디스크 기록
User user = userRepository.findById(userId).orElseThrow(
() -> new IllegalArgumentException("Not Found User")
);
Image newImage = Image.builder()
.location(request.getLocation())
.caption(request.getCaption())
.postImage(uuidFilename)
.tags(new ArrayList<>()) // builder로 엔티티 생성시 초기화 하지 않으면 null값이 들어가게 됨
.build();
newImage.setUser(user);
imageRepository.save(newImage);
tagParsing(newImage.getImageId(), request.getTags());
}
1) 파일을 업로드하기 위해서 유니크한 파일명을 가져야 합니다.
✔️ 중복된 파일명을 가지지 않기 위해서 UUID.randomUUID()을 사용합니다.
html form 태그로부터 데이터를 전달받아 ImageUploadDTO를 통해 전달받아 처리합니다.
2) 아래에 DTO 속성이 있으며, file을 전달받기 위해서는 자료형을 MultipartFile을 사용해야 합니다.
(form 태그로 전달받은 값을 초기화하기 위해서 DTO에 Setter가 지정되어 있어야 합니다.!!)
3) uuid 값과 file의 이름을 합쳐 고유한 값을 만들어 줍니다.
file의 이름은 file.getOriginalFilename() 을 통해 가져올 수 있습니다.
4) 저장할 파일의 이름을 설정했으면, 파일을 저장할 위치를 설정합니다.
저장할 위치는 Path을 통해 정합니다.
Paths.get(fileRealPath + uuidFilename)을 통해 위치를 지정합니다.
5) Files.write(filepath, file.getBytes()) 을 통해 파일을 실제 다드 디스크에 저장합니다.
DTO Class
@Data
@NoArgsConstructor
public static class ImageUploadDTO{
private MultipartFile file;
private String caption;
private String location;
private String tags;
}
파일 처리가 완료되면 Image 엔티티를 영속화시켜 데이터베이스에 저장해 줍니다.
Builder 패턴을 통해 전달받은 값과 처리한 파일 데이터를 저장합니다.
Builder 패턴을 사용해 Image 객체를 생성하므로 추후에 tags를 설정하기 위해서는 new ArrayList<>() 빈 리스트 값을 넣어주어야 합니다.
값을 설정하지 않게 될 경우 null값으로 자동 설정 되어 추후에 newImage에 tags 속성에 접근하려고 할 때 NullException이 발생하게 됩니다.
#해시태그 파싱하기
public void tagParsing(Long imageId, String tags){
Image image = imageRepository.findById(imageId).get();
List<String> tagList = Utils.tagParser(tags);
for (String tag : tagList){
Tag imageTag = Tag.builder()
.name(tag)
.build();
imageTag.setImage(image);
tagRepository.save(imageTag);
}
}
public static List<String> tagParser(String tags){
String[] temp = tags.split("#");
// temp = [, hello, 안녕, 바이]
int len = temp.length;
return new ArrayList<>(Arrays.asList(temp).subList(1, len));
}
전달받은 tags에는 해시태드 값이 저장되어 있습니다.
위 로직은 #hello#여행#코딩 으로 작성되어 처리함을 가정하고 있습니다.
tags.split("#")을 통해 # 을 기준으로 분리합니다.
0번째 인덱스에 빈 값이 저장되므로 우리는 1부터 temp.length 까지의 값을 사용합니다.
HTML 파일 - 파일 전송하기
<form th:action="@{/image/uploadProc}" method="post" enctype="multipart/form-data">
<input id="input_img" type="file" name="file" placeholder="사진파일">
</form>
action과 method에 경로와 Http 메서드 전송 방식을 설정합니다.
파일을 전달하는 경우 enctype = "multipart/form-data" 를 작성해 주어야 합니다.
또한, input 태그에 type = "file"로 설정해 파일을 업로드합니다.
'Spring Framework > Spring' 카테고리의 다른 글
[Spring Cloud] Eureka Server, Discovery Service 이해하기 (0) | 2024.03.31 |
---|---|
[Spring] Spring CORS 설정 & 이슈 해결 및 웹 애플리케이션 통신 이해하기 (0) | 2024.02.24 |
[SPRING] Spring 객체지향 설계 solid 원칙 이해하기 - Spring Container, IoC, DI (1) | 2024.02.07 |
[Spring] 스프링 중복 빈 해결 방법, Bean이 2개 이상일 때 (0) | 2023.04.01 |
[Spring] 스프링 싱글톤 컨테이너, 스프링 컨테이너 (0) | 2023.03.28 |