글을 정리하다가
이미지 업로드 구현 연습하려고 만들었던 깃을 발견했다.
나는 너무 게으른가봐ㅜㅠㅠ
전 글에서 FileOutputStream 클래스를 이용해서 파일을 등록하고 삭제하는 FileService 클래스를 구현했다.
이번에는 파일 중에서 이미지만을 등록, 수정, 삭제하는 비즈니스 로직이 담긴 PostImgService 클래스를 구현할 것이다.
PostImgService 는 FileService 를 변수로 선언해서 사용한다.
PostImgService
package com.example.blog.service;
import com.example.blog.entity.ImgEntity;
import com.example.blog.repository.ImgRepository;
import lombok.RequiredArgsConstructor;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;
import org.thymeleaf.util.StringUtils;
import javax.transaction.Transactional;
import java.util.List;
// 글에 이미지 업로드
@Service
@RequiredArgsConstructor
@Transactional
public class PostImgService {
@Value("${itemImgLocation}") // .properties 의 itemImgLocation 값을 itemImgLocation 변수에 넣어줌
private String imgLocation;
private final FileService fileService;
private final ImgRepository imgRepository;
// 이미지 저장
// MultipartFile 인터페이스를 이용해서 업로드 한 파일의 이름, 실제 데이터, 파일 크기 등을 구할 수 있다.
public void savePostImg(ImgEntity imgEntity, MultipartFile imgFile) throws Exception {
/*
imgName: 실제 로컬에 저장된 이미지 파일 이름
oriImgName: 업로드했던 이미지 파일 초기 이름
imgUrl: 업로드 결과 로컬에 저장된 이미지 파일을 불러올 경로
*/
String oriImgName = imgFile.getOriginalFilename();
String imgName = "";
String imgUrl = "";
if (!StringUtils.isEmpty(oriImgName)) {
// 이미지 이름 = 이미지경로 + 파일이름 + 파일크기
imgName = fileService.uploadFiles(imgLocation, oriImgName, imgFile.getBytes());
// 최종 이미지 경로
imgUrl = "/item/" + imgName;
}
imgEntity.setImgName(imgName);
imgEntity.setOriImgName(oriImgName);
imgEntity.setImgUrl(imgUrl);
imgRepository.save(imgEntity);
}
// 이미지 수정
public void updateImg(Long imgId, MultipartFile imgFile) throws Exception{
// 수정할 이미지 id 조회
if(!imgFile.isEmpty()){
ImgEntity imgSaveEntity = imgRepository.findById(imgId).orElse(null);
// 기존 이미지 파일 삭제
if (!StringUtils.isEmpty(imgSaveEntity.getImgName())){
fileService.deleteFile(imgLocation + "/" + imgSaveEntity.getImgName());
}
// 수정한 이미지 파일 저장
String oriImgName = imgFile.getOriginalFilename();
String imgName = fileService.uploadFiles(imgLocation,oriImgName,imgFile.getBytes());
String imgUrl = "/item/" + imgName;
// 1. setter 로 넣기
// imgSaveEntity.setOriImgName(oriImgName);
// imgSaveEntity.setImgName(imgName);
// imgSaveEntity.setImgUrl(imgUrl);
// 2. 만들어줬던 메소드로 넣기_파라미터 entity
// imgSaveEntity.imgPatch(new ImgEntity(imgName, oriImgName,imgUrl));
// 3. 만들어줬던 메소드로 넣기_파라미터 변수
imgSaveEntity.imgUpdate(imgName, oriImgName,imgUrl);
}
}
// 이미지 삭제
public void deleteImg(Long postDtoId){
List<ImgEntity> imgEntities = imgRepository.findByPostEntityIdOrderByIdAsc(postDtoId);
for(int i=0; i<imgEntities.size();i++) {
imgRepository.delete(imgEntities.get(i));
}
}
}
⭐ 이미지 저장
// 이미지 저장
// MultipartFile 인터페이스를 이용해서 업로드 한 파일의 이름, 실제 데이터, 파일 크기 등을 구할 수 있다.
public void savePostImg(ImgEntity imgEntity, MultipartFile imgFile) throws Exception {
/*
imgName: 실제 로컬에 저장된 이미지 파일 이름
oriImgName: 업로드했던 이미지 파일 초기 이름
imgUrl: 업로드 결과 로컬에 저장된 이미지 파일을 불러올 경로
*/
String oriImgName = imgFile.getOriginalFilename();
String imgName = "";
String imgUrl = "";
if (!StringUtils.isEmpty(oriImgName)) {
// 이미지 이름 = 이미지경로 + 파일이름 + 파일크기
imgName = fileService.uploadFiles(imgLocation, oriImgName, imgFile.getBytes());
// 최종 이미지 경로
imgUrl = "/item/" + imgName;
}
imgEntity.setImgName(imgName);
imgEntity.setOriImgName(oriImgName);
imgEntity.setImgUrl(imgUrl);
imgRepository.save(imgEntity);
}
DB 와 접근할 수 있는 entity 데이터로만 비즈니스 로직을 구현한다.
FileService 에서 선언한 uploadFiles 메소드로 이미지 이름과 이미지 경로를 넣어준다.
ImgEntity 의 setter 를 이용해 값을 변수에 넣어준다.
그리고 Repository 의 save 메소드로 데이터를 DB 에 저장한다.
⭐ 이미지 수정
// 이미지 수정
public void updateImg(Long imgId, MultipartFile imgFile) throws Exception{
// 수정할 이미지 id 조회
if(!imgFile.isEmpty()){
ImgEntity imgSaveEntity = imgRepository.findById(imgId).orElse(null);
// 기존 이미지 파일 삭제
if (!StringUtils.isEmpty(imgSaveEntity.getImgName())){
fileService.deleteFile(imgLocation + "/" + imgSaveEntity.getImgName());
}
// 수정한 이미지 파일 저장
String oriImgName = imgFile.getOriginalFilename();
String imgName = fileService.uploadFiles(imgLocation,oriImgName,imgFile.getBytes());
String imgUrl = "/item/" + imgName;
// 1. setter 로 넣기
// imgSaveEntity.setOriImgName(oriImgName);
// imgSaveEntity.setImgName(imgName);
// imgSaveEntity.setImgUrl(imgUrl);
// 2. 만들어줬던 메소드로 넣기_파라미터 entity
// imgSaveEntity.imgPatch(new ImgEntity(imgName, oriImgName,imgUrl));
// 3. 만들어줬던 메소드로 넣기_파라미터 변수
imgSaveEntity.imgUpdate(imgName, oriImgName,imgUrl);
}
}
DB 와 접근할 수 있는 entity 데이터로만 비즈니스 로직을 구현한다.
Repository 의 findByID 메소드로 수정할 이미지의 id 를 찾는다.
찾은 이미지 id 를 이용해서 기존의 이미지를 삭제한다.
그리고 수정한 이미지를 다시 저장하기 위해서
FileService 에서 선언한 uploadFiles 메소드로 이미지 이름과 이미지 경로를 넣어준다.
(주석) ImgEntity 의 setter 를 이용해 값을 변수에 넣어준다.
또는 (주석) imgPath 메소드를 이용해 새롭게 값을 넣어준다.
또는 imgUpeate 메소드를 이용해 변수에 넣어준다.
이렇게 변수에 값을 넣는 방법을 여러 개로 구현해 본 이유는
어떤 방법이 더 효율적일지 테스트 해볼 목적이었지만
메모리관리같은 부분을 잘 몰라서 그런지 감이 안왔다.🤣
아무튼 저 셋 중 한 방법으로 구현하면 된다.
댓글