Development note/Java

[Java] 서블릿 환경에서 현재 실행 디렉토리 가져오기

v명월v 2019. 10. 16. 09:00

안녕하세요. 명월입니다.


이 글은 Java 서블릿 환경에서 현재 실행 디렉토리 가져오기에 대한 설명입니다.


프로그램을 작성하다 보면 현재 실행되고 있는 디렉토리를 알아야 할 때가 있습니다. 예를 들면 환경 파일을 읽어야 한다거나 프로젝트상의 파일을 읽어야 할 때 필요하겠습니다.

이 현재 로컬 디렉토리를 알 수 있는 방법은 두 가지가 있습니다.


먼저 현재 클래스의 위치를 찾는 것입니다.

import java.io.IOException;
import java.io.PrintWriter;
import java.net.URL;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

@WebServlet("/Where")
public class Where extends HttpServlet {
  private static final long serialVersionUID = 1L;

  public Where() {
    super();
  }

  protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    PrintWriter writer = response.getWriter();
    writer.append("This file directory is ...   ");
    
    // 현재 실행되고 있는 클래스의 위치를 찾는다.
    URL url = Thread.currentThread().getContextClassLoader().getResource(this.getClass().getName() + ".class");
    writer.append(url.getPath());
  }

  protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    doGet(request, response);
  }
}

이렇게 하면 현재 실행되고 있는 클래스 파일의 위치가 나오기 때문에 현재 실행 경로를 알 수 있습니다. 저의 경우는 Thread.currentThread를 사용했는데, 현재 실행 중인 스래드라는 표시입니다.

이게 문제가 될 수 있는 요지(lambda식이던가 멀티스레드)가 있기 때문에 Thread.currentThread().getContextClassLoader() 대신에 this.getClass().getClassLoader()로 바꾸어 사용할 수도 있습니다.


또 하나의 방법은 서블릿의 context를 이용하는 방법입니다.

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

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

@WebServlet("/Where")
public class Where extends HttpServlet {
  private static final long serialVersionUID = 1L;

  public Where() {
    super();
  }

  protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    PrintWriter writer = response.getWriter();
    writer.append("This project directory is ...   ");

    // servletContext에서 현재 경로를 가져온다.
    String path = getServletContext().getRealPath("/");
    writer.append(path);
  }

  protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    doGet(request, response);
  }
}

개인적으로 자주 사용하는 방법입니다. 이거는 클래스의 위치를 찾는 것보다는 프로젝트의 Root 패스를 리턴해 줍니다. 위에는 클래스의 위치를 찾는 것이 때문에 classes 디렉토리와 class 파일도 다 나옵니다. 다른 디렉토리를 가려면 문자 치환이 필요합니다.

그러나 밑은 완벽히 프로젝트 root를 사용하기 때문에 사용하기는 편합니다. 그러나 servlet의 context를 가져와야 하기 때문에 Sevlet 파일이 아니면 사용할 수 없겠네요.


방법으로는 web.xml에서 시작 프로그램을 만든 다음, 거기에 static 변수로 path를 초기화 시키면 편리하게 사용할 수 있습니다.

링크 - [Java강좌 - 58] Java servlet에서 인스턴스 초기화하는 방법


여기까지 Java 서블릿 환경에서 현재 실행 디렉토리 가져오기에 대한 설명이었습니다.


궁금한 점이나 잘못된 점이 있으면 댓글 부탁드립니다.