230403 Spring_FileUpload

Myung A Lee·2023년 4월 3일
0

Spring

목록 보기
3/6
post-thumbnail

Spring

File 관련 설정

라이브러리 등록 pome.xml

		<!-- https://mvnrepository.com/artifact/commons-fileupload/commons-fileupload -->
		<dependency>
		    <groupId>commons-fileupload</groupId>
		    <artifactId>commons-fileupload</artifactId>
		    <version>1.3.3</version>
		</dependency>
		
		<!-- https://mvnrepository.com/artifact/commons-io/commons-io -->
		<dependency>
		    <groupId>commons-io</groupId>
		    <artifactId>commons-io</artifactId>
		    <version>2.6</version>
		</dependency>

root-context.xml

	<bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver">
		<property name="defaultEncoding" value="UTF-8"/>
		<property name="maxInMemorySize" value="10000000"/>
		<property name="maxUploadSize" value="10000000"/>
	</bean>
	
	<!-- fileSizeThreshold : 파일이 디스크에 기록될 때 까지의 크기 임계값(byte) -->
	<!-- maxFileSize : 업로드 할 파일에 허용되는 최대 크기 -->

Servers/server.xml

<Context docBase="07_FileServie" path="/gudi" reloadable="true" source="org.eclipse.jst.jee.server:07_FileServie"/>

<!-- 다음 내용을 추가 : "/gudi 요청이 오면 07_FileServie 로 연결"의 의미 -->
<Context docBase="C:/img/upload" path="/photo"/>

</Host>

File Upload

1. view (jsp)

  • 파일 전송 규칙에 맞춰 form 태그 생성

    파일 전송 규칙
    규칙 1. 무조건 Post 방식으로 전송해야 한다.
    규칙 2. 보내는 파라메터의 type이 문자 외에도 여러가지(multipart)로 구성되어 있다고 알려야한다.
    규칙 3. 파일의 크기를 제한해 줘야 한다. (컨트롤러에서 지정)

<form action="upload.do" method="post" enctype="multipart/form-data">
		<input type="text" name="title"/>
		<input type="file" name="uploadFile"/>
		<input type="submit" value="전송"/>
	</form>

2. Controller

  • 형식에 맞춰 Service 호출
@RequestMapping(value="/upload.do", method = RequestMethod.POST)
	public String upload(MultipartFile uploadFile, @RequestParam String title) {
		
		logger.info("일반 파라메터 : " + title);
		
		service.upload(uploadFile);
		
		return "redirect:fileList.do";
	}

3. Service

  • 파일 업로드 순서에 맞춰 진행

    파일 업로드
    1 업로드 할 파일의 경로를 지정 (존재하지 않는다면 Error)
    2 파일명을 추출. 이때 사용자가 늘어나면 파일명이 겹칠 확률이 높아지기 때문에 업로드 시간을 이용하거나 해시코드를 이용하여 새로운 저장명을 만드는 것을 권장
    3 파일 저장

String root = "C:/img/upload/";
	public void upload(MultipartFile file) {
		
		// 1. 파일명 추출
		String fileName = file.getOriginalFilename();
	
		// 사용자가 많아지면 파일명이 겹칠 확률이 매우 높음
		// 따라서, 겹치지 않는 파일명을 생성할 필요가 있음
		// 1.파일업로드 시간을 이용 2. 해시코드 이용
		
		// 파일 확장자를 추출하여 따로 저장 (photo.jpg)
		int index = fileName.lastIndexOf(".");
		String ext = fileName.substring(index);
		
		// 새로운 파일명 생성 (파일업로드 현재 시간을 기준)
		long time = System.currentTimeMillis();
		// 추출해 놓은 확장자를 다시 붙여줌
		String newFileName = time+ext;
		
		logger.info("파일 명 : "+fileName +" => "+ newFileName);
		
		
		// 2. 파일 저장
		try {
			
			byte[] bytes = file.getBytes();
			// JAVA NIO 사용 - 일단 Path이용해서 경로 설정
			Path path = Paths.get(root + newFileName);
			Files.write(path, bytes);
			
		} catch (IOException e) {
			e.printStackTrace();
		}
	}

File List

view

	<c:if test="${list.size()==0}">
		<h3>업로드 된 사진이 없습니다. </h3>
	</c:if>
	<c:if test="${list.size()>0}">
		<c:forEach items="${list}" var="path">
			<img src="${path}" width="250"/>
			<a href="delete?file=${fn:split(path,'/')[1]}">삭제</a>
			<br/>
		</c:forEach>
	</c:if>

Controller

@RequestMapping(value="/fileList.do")
	public String fileList(Model model) {
		logger.info("fileList 요청");
		ArrayList<String> list = service.fileList();
		
		logger.info("list size : " + list.size());
		model.addAttribute("list", list);
		
		return "list";
	}

Service

public ArrayList<String> fileList() {
		
		ArrayList<String> pathList = new ArrayList<String>();
		
		File[] files = new File(root).listFiles();
		
		for(File file : files) {
			logger.info("file name :" + file.getName());
			pathList.add("/photo/" + file.getName());
		}
		
		return pathList;
	}

File Delete

Service

public void delete(String file) {
		// 1, File 객체 생성
		File delFile = new File(root+file);
		// 2. 지울 파일이 있다면
		if(delFile.exists()) {
			// 3.삭제
			delFile.delete();
		}
	}

File MultiUpload

View

<form action="mutiupload.do" method="post" enctype="multipart/form-data">
		<input type="file" name="uploadFiles" multiple="multiple"/>
		<input type="submit" value="전송"/>
	</form>

Service

public void multiupload(MultipartFile[] uploadFiles) {
		
		// 배열로 넘어온 파일을 하나하나씩 업로드해주는 과정
		// 업로드는 upload method에 이미 구현 되어 있음
		for (MultipartFile file : uploadFiles) {
			upload(file);
			
			// for문이 굉장히 빠르기 때문에 강제로 시간차를 둬서 파일 저장명을 다르게 해줌 
			try {
				Thread.sleep(1);
			} catch (InterruptedException e) {
				e.printStackTrace();
			}
		}
		
	}

0개의 댓글