자바(JAVA)/JSP 웹 프로그래밍 공부 (성낙현의 JSP 자바 웹 프로그래밍 참고)

JAVA/JSP 36. 파일 업로드 및 다운로드 - 파일 목록 보기, 파일 다운로드

개발학생 2025. 4. 25. 16:56
반응형

*JAVA/JSP 35번 글의 시점부터는 노트북이 고장나는 바람에.. 다른 분의 글과 이전에 올렸던 글들을 참고하여, 다른 데스크탑의 윈도우 환경에 환경설정을 다시 진행한 후 작성하였습니다. 환경설정 관련 글들은 아래를 참고해 주세요.

  • JDK11 설치 및 환경 변수(JAVA_HOME) 설정 - CLASSPATH는 추가하지 않음
 

자바(JAVA) 11 설치 및 환경설정 | 자바 11 환경 변수

자바로 코딩 공부를 하려면 개발 할 수 있는 환경을 만들어 주어야 한다. 그 순서를 먼저 작성하자면JAVA SE JDK 설치 -> JAVA 환경 변수 설정 -> IDE 설치 이렇게 볼 수 있겠다. 이 포스팅은 자바로 개

velog.io

  • 톰캣 설치, 이클립스 설치 - 이 글을 쓰는 시점에서는 Tomcat 8버전이 없어, Tomcat 9버전 설치
 

JSP) JDK, 이클립스(eclipse), 톰캣 설치 및 환경 설정

1. JDK 설치 → Path 설정 2.eclipse JAVA EE버전 다운로드 3.웹컨테이너 톰캣 설치 →톰캣 환경설정 1. JDK 설치 - JAVA) 1. JDK 참고하여 설치하고 설정한다. -https://storyblogger.tistory.com/15?category=984696 2. 구글에

storyblogger.tistory.com

  • 이클립스 JDK 버전 설정 - JDK11로 설정
 

[이클립스] JDK 버전 바꾸는 법

스프링을 사용하는 에러가 난다? 그러면 JRE 버전을 확인해보자! 프로젝트의 JRE System Library의 오른쪽을 살펴보면 [JavaSE-17]이라고 되어있다. 스프링이나 하이버네이트를 사용할 때, 자바 8이나 자

myvelop.tistory.com

  • JDK 설치 및 환경 변수(JAVA_HOME) 설정, 톰캣 설치, 이클립스 설치 및 JDK 버전 설정 이후~ ⇒ 톰캣 버전과 jsp 파일 경로는 글 내용과 다르게 아래 이미지와 같음

 

JAVA/JSP 1. 개발 환경 구축 - 이클립스 기본 설정

*JDK 설치 및 환경 변수(JAVA_HOME) 설정, 톰캣 설치, 이클립스 설치를 완료한 상태OpenJDK 11: 자바 프로그램을 컴파일하고 실행해주는 기본 도구*이클립스 JDK-17이 설치되어있어서, https://coding-house.tisto

keep-programming-study.tistory.com

 

 

JAVA/JSP 1. 개발 환경 구축 - JSP 예제 테스트

1. 프로젝트 생성1) [File] → [New] → [Dynamic Web Project] 선택 2) 프로젝트 설정 화면 → Project name: HelloJSP, Target runtime: Apache Tomcat v9.0, Dynamic web module version: 4.0으로 설정 후 Next 클릭 3) 자바 소스 파일

keep-programming-study.tistory.com

 

 

JAVA/JSP 1. 개발 환경 구축 - 마지막 추가 설정

1. 외부 웹 브라우저로 실행하기-크롬이클립스는 웹 애플리케이션 실행 시, 자체 브라우저를 통해 실행 결과 출력웹 애플리케이션 배포 시 사용자는 크롬/파이어폭스 같은 전용 웹 브라우저로

keep-programming-study.tistory.com

  • 오라클(Oracle Database 11gR2 Express Edition) 설치 및 설정 
 

JAVA/JSP 14. 데이터베이스 - 특징, 오라클 설치(Oracle Database 11gR2 Express Edition), 사용자 계정 생성 및

1. 데이터베이스의 특징우리가 매일 PC나 스마트폰을 통해 접하는 거의 모든 웹 애플리케이션에서 사용함매일 업데이트되는 뉴스나 날씨 등의 정보는 데이터베이스가 없다면 클라이언트에 전달

keep-programming-study.tistory.com

 

 

 

JAVA/JSP 15. 데이터베이스 - 테이블 및 시퀀스 생성, JDBC 설정 및 데이터베이스 연결

*회원제 게시판 만들기-회원 인증 필요4. 테이블 및 시퀀스 생성1) 테이블 생성(1) member 테이블 - 아이디, 패스워드, 이름, 가입 날짜테이블 정의컬럼명데이터 타입 null 허용 키 기본값 설명idvarchar2

keep-programming-study.tistory.com

 

JAVA/JSP 16. 데이터베이스 - 커넥션 풀로 성능 개선, 간단한 쿼리 작성 및 실행

6. 커넥션 풀로 성능 개선웹은 클라이언트의 요청에 서버가 응답하는 구조→ Connection 객체 생성 때마다 네트워크 통신이 이뤄지며, 시간이 걸리는 작업들이 수반됨 == 시스템 성능에 큰 영향을

keep-programming-study.tistory.com

  • 시퀀스 설정
 

JAVA/JSP 15. 데이터베이스 - 테이블 및 시퀀스 생성, JDBC 설정 및 데이터베이스 연결

*회원제 게시판 만들기-회원 인증 필요4. 테이블 및 시퀀스 생성1) 테이블 생성(1) member 테이블 - 아이디, 패스워드, 이름, 가입 날짜테이블 정의컬럼명데이터 타입 null 허용 키 기본값 설명idvarchar2

keep-programming-study.tistory.com

 

1. 파일 목록 보기

1) MyfileDAO에 파일 목록을 가져오는 메서드 추가

// Java Resources/src/fileUpload/MyfileDAO.java
import java.util.List;
import java.util.Vector;
...생략...

public class MyfileDAO extends DBConnPool {
  ...생략...
    
  // 파일 목록 반환
  public List<MyfileDTO> myFileList() {
    List<MyfileDTO> fileList = new Vector<MyfileDTO>();  // 1. List 컬렉션(Vector) 생성
		
    // 2. SELECT 쿼리문 작성: 일련번호를 내림차순으로 정렬하여 최신 게시물이 먼저 출력되게 함
    String query = "SELECT * FROM myfile ORDER BY idx DESC";    
    try {
      // 3. 쿼리 준비: 정적 쿼리문 샐행을 위해 Statement 객체 생성
      psmt = con.prepareStatement(query); 
      // 4. 쿼리문 실행(반환 타입은 ResultSet)
      rs = psmt.executeQuery();
			
      // 5. 목록 안의 파일 수만큼 반복 -> ResultSet에 포함된 레코드 수만큼 반복
      // -> next()메서드로 출력할 레코드가 있는지 확인하고 커서 이동
      while (rs.next()) {    
        // 6. DTO 객체를 생성하고 각 컬럼의 값을 추출하여 저장
        // -> 컬럼 순서대로 인덱스를 이용해 추출
        MyfileDTO dto = new MyfileDTO();
        dto.setIdx(rs.getString(1));
        dto.setName(rs.getString(2));
        dto.setTitle(rs.getString(3));
        dto.setCate(rs.getString(4));
        dto.setOfile(rs.getString(5));
        dto.setSfile(rs.getString(6));
        dto.setPostdate(rs.getString(7));
				
        // 7. 레코드 내용이 담긴 DTO 객체를 List 컬렉션에 저장
        fileList.add(dto);
      }
    } catch (Exception e) {
      System.out.println("SELECT 시 예외 발생");
      e.printStackTrace();
    }
		
    // 8. 결과 레코드를 모두 저장한 List 객체를 반환
    return fileList;
  }
}

2) 파일 목록을 출력하는 FileList.jsp 새로 생성

// src/main/webapp/FileList.jsp
<%@page import="java.net.URLEncoder"%>
<%@page import="fileupload.MyfileDTO"%>
<%@page import="java.util.List"%>
<%@page import="fileupload.MyfileDAO"%>
<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>FileUpload</title>
</head>
<body>
  <h2>DB에 등록된 파일 목록 보기</h2>
  <a href="FileUploadMain.jsp">파일 등록하기</a>    <!-- 1. 작성폼으로 이동하는 하이퍼링크-->
  <%
  MyfileDAO dao = new MyfileDAO();    // 2. DAO 객체를 생성
  List<MyfileDTO> fileLists = dao.myFileList();     // 3. 파일 목록을 얻어옴
  dao.close();
  %>
  <table border="1">
    <tr>
      <th>No</th><th>작성자</th><th>제목</th><th>카테고리</th>
      <th>원본 파일명</th><th>저장된 파일명</th><th>작성일</th>
    </tr>
  <!-- 4. 3에서 반환받은 값을 이용해서 목록을 반복 출력(DTO객체의 getter 활용) -->
  <% for (MyfileDTO f : fileLists) { %>
    <tr>
      <td><%= f.getIdx() %></td>
      <td><%= f.getName() %></td>
      <td><%= f.getTitle() %></td>
      <td><%= f.getCate() %></td>
      <td><%= f.getOfile() %></td>
      <td><%= f.getSfile() %></td>
      <td><%= f.getPostdate() %></td>
      <!-- 5. 파일을 다운로드하기 위한 링크(다운로드 기능은 나중에 만들 예정) -->
      <td><a href="Download.jsp?oName=<%= URLEncoder.encode(f.getOfile(), 
        "UTF-8") %>&sName=<%= URLEncoder.encode(f.getSfile(), "UTF-8") %>">[다운로드]</a></td>
    </tr>
  <% } %>
  </table>
</body>
</html>

3) FileList.jsp 우클릭하고, Run As -> Run On Server를 클릭하여 실행

2. 파일 다운로드 

1) 자바스크립트 함수를 편하게 사용하기 위해, JSFunction.java 생성

// Java Resources/src/utils/JSFunction.java
package utils;

import java.io.IOException;
import java.io.PrintWriter;

import javax.servlet.jsp.JspWriter;

public class JSFunction {
    public void alertBack(String message, PrintWriter out) {
        out.println("<script>alert('" + message + "'); history.back();</script>");
        out.flush();
    }
    
    // JspWriter도 받을 수 있도록 오버로딩
    public static void alertBack(String message, JspWriter out) {
        try {
            out.println("<script>alert('" + message + "'); history.back();</script>");
            out.flush();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

2) 파일을 다운로드하는 Download.jsp 새로 생성

// src/main/webapp/Download.jsp
<%@page import="utils.JSFunction"%>
<%@page import="java.io.FileNotFoundException"%>
<%@page import="java.io.OutputStream"%>
<%@page import="java.io.FileInputStream"%>
<%@page import="java.io.InputStream"%>
<%@page import="java.io.File"%>
<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<%
// 1. Uploads 폴더의 물리적 경로 얻어오기 
String saveDirectory = application.getRealPath("/Uploads");
// 2. 저장된 파일명과 원본 파일명을 매개변수로 받아서 변수에 저장
String saveFilename = request.getParameter("sName");
String originalFilename = request.getParameter("oName");

try {
  // 3. 해당 파일을 찾아 입력 스트림 생성
  File file = new File(saveDirectory, saveFilename);
  InputStream inStream = new FileInputStream(file);
	
  // 한글 파일명 깨짐 방지 
  // 4. request 내장 객체를 통해 요청 헤더 중 User-Agent를 읽어옴
  String client = request.getHeader("User-Agent");
  // 5. 파일명이 한글일 경우 깨짐 방지를 위한 처리, 
  // 웹브라우저가 인터넷 익스플로러가 아닌 경우 getBytes("UTF-8")로 원본 파일명을 바이트 배열로 변환한 후, ISO-8859-1 캐릭터셋의 문자열로 재생성
  // 웹브라우저가 인터넷 익스플로러면 getBytes("KSC5601")을 이용하여 바이트 배열로 변환한 후, ISO-8859-1 캐릭터셋의 문자열로 재생성
  if(client.indexOf("WOW64") == -1) {
    originalFilename = new String(originalFilename.getBytes("UTF-8"), "ISO-8859-1");
  } else {
    originalFilename = new String(originalFilename.getBytes("KSC5601"), "ISO-8859-1");
  }
	
  // 파일 다운로드용 응답 헤더 설정
  // 6. 응답 헤더를 초기화
  response.reset();
  // 7. 파일 다운로드 창을 띄우기 위한 콘텐츠 타입 지정(octet-stream은 8비트 단위의 바이너리 데이터)
  // -> 파일 종류에 상관없이 웹브라우저는 다운로드 창을 띄움
  response.setContentType("application/octet-stream");
  // 8. 웹브라우저에서 파일 다운로드 창이 뜰 때, 원본 파일명이 기본으로 입력되어 있도록 설정
  response.setHeader("Content-Disposition", "attachment; filename=\"" + originalFilename + "\"");
	
  // 9. 새로운 출력 스트림을 생성하기 위해, 출력 스트림 초기화(이 부분이 없으면 예외 발생)
  out.clear();
	
  // 10. response 내장 객체로부터 새로운 출력 스트림 생성
  OutputStream outStream = response.getOutputStream();
	
  // 11. 출력 스트림에 따른 파일 내용 출력
  byte b[] = new byte[(int)file.length()];
  int readBuffer = 0;
  while( (readBuffer = inStream.read(b)) > 0 ) {
    outStream.write(b, 0, readBuffer);
  }
	
  // 12. 입/출력 스트림 닫음
  inStream.close();
  outStream.close();
} catch (FileNotFoundException e) {
  JSFunction.alertBack("파일을 찾을 수 없습니다.", out);
} catch (Exception e) {
  JSFunction.alertBack("예외가 발생하였습니다.", out);
}
%>

 

3) FileList.jsp 우클릭하고, Run As -> Run On Server를 클릭하여 실행한 후 [다운로드] 클릭

  • 파일이 원본 파일명으로 정상적으로 다운로드 됨

반응형