[23/06/19] JSP (3)

yeju·2023년 6월 19일
0

JSP

목록 보기
4/7
post-thumbnail

📌 예외 처리

예기치 못한 오류가 발생했을 때 코드상으로 적절하게 그 오류에 대한 처리를 하는 것
오류가 발생하면 기본적으로 웹 서버가 제공하는 오류 페이지가 나오는데, 해당 페이지는 서버 버전, 디렉토리 구조 등 페이지에 대한 정보가 나와 있어 보안이 취약하기 때문에 예외 처리를 직접 해야 함

📝 1. page 디렉티브 태그 이용해 예외 처리하기

errorPage 속성 : 호출할 오류 페이지의 URL을 지정
오류가 발생하면 웹 서버의 기본 오류 페이지 대신 지정한 페이지가 호출

<%@ page errorPage="오류 페이지 URL" %>

isErrorPage 속성 : true로 설정하면 현재 페이지를 오류 페이지로 지정
해당 페이지에서 exception 내장 객체를 사용할 수 있음

<%@ page isErrorPage="true" %>

📄 [예제] page 디렉티브 태그로 숫자 나누기 예외 처리

파일명 : exception.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>예외 처리</title>
</head>
<body>
    <!-- 숫자 두개를 입력받는 폼 태그 -->
	<form action="exception_process.jsp" method="post">
		<p>숫자1 : <input type="text" name="num1"></p>
		<p>숫자2 : <input type="text" name="num2"></p>
		<p><input type="submit" value="나누기"></p>
	</form>
</body>
</html>
파일명 : exception_process.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<%-- 에러가 나면 다음 페이지로 이동 --%>
<%@ page errorPage="exception_error.jsp" %>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>예외 처리</title>
</head>
<body>
	<%
		String num1 = request.getParameter("num1");
		String num2 = request.getParameter("num2");
		int a = Integer.parseInt(num1);
		int b = Integer.parseInt(num2);
		int c = a / b;
		out.print(num1 + " / " + num2 + " = " + c);
	%>
</body>
</html>
파일명 : exception_error.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<%-- 이 페이지를 예외 처리 페이지로 지정, exception 내장 객체 메서드 사용 가능 --%>
<%@ page isErrorPage="true" %>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>오류 페이지</title>
</head>
<body>
	<p>오류가 발생했습니다.</p>
	<p>예외 : <%= exception %></p>
	
	<p>toString() : <%= exception.toString() %></p>
	<p>getClass().getName() : <%= exception.getClass().getName() %></p>
	<p>getMessage() : <%= exception.getMessage() %></p>
</body>
</html>

exception.jsp 는 폼 태그에 숫자를 입력 후 제출해 exception_process.jsp 에서 두 숫자를 나누어 출력하는 페이지이다. 입력한 값이 문자이거나, 나누는 수가 0인 경우 등 오류가 발생하면 exception_error.jsp 페이지로 이동해 오류와 관련된 내용을 출력한다.

💻 실행 결과

📝 2. web.xml 파일 이용해 예외 처리하기

web.xml 이란?
서버가 최초에 시작될 때(run) 초기 설정을 어떻게 할지 적어놓은 설명서
webapp/WEB-INF 폴더 내에 있어야 한다.

[이미 생성된 프로젝트에 web.xml 만들기]
프로젝트명 우클릭 : Java EE Tools - Generate deployment descriptor stub

web.xml 파일에 error-page 코드를 작성해 오류를 처리할 수 있다.

web.xml 의 <web-app></web-app> 태그 내에 해당 코드 추가
<error-page>
  <error-code>오류 코드 (ex. 500)</error-code>
  <location>이동할 오류 페이지의 URI</location>
  <!-- webapp 폴더 내의 파일 경로는 /파일명 (ex. /error.jsp) -->
</error-page>
<error-page>
  <exception-type>예외 유형</exception-type>
  <location>이동할 오류 페이지의 URI</location>
</error-page>

오류가 발생했을 때 오류 코드 또는 예외 유형이 일치하면 지정한 오류 페이지로 이동

💡 주요 오류 코드

코드설명
4xx클라이언트 오류
400클라이언트의 요청 구문이 잘못됨
401접근이 허용되지 않음 (인증 안함)
403사용자가 리소스에 대한 필요 권한을 갖고 있지 않음
404요청한 페이지를 찾을 수 없음
5xx서버 오류
500서버 내부 에러 (JSP에서 예외 발생)
503서버가 일시적으로 서비스를 제공하지 않음 (서버 과부하 및 보수중)

📝 3. try-catch-finally 문으로 예외 처리하기

자바의 예외 처리 구문 (try-catch) 을 스크립틀릿 태그에 작성한다.

📄 [예제] try-catch 문으로 숫자 나누기 예외 처리

위 예제와 동일한 숫자 입력폼 html 사용

파일명 : exception_process.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>예외 처리</title>
</head>
<body>
	<%
		try {
			String num1 = request.getParameter("num1");
			String num2 = request.getParameter("num2");
			int a = Integer.parseInt(num1);
			int b = Integer.parseInt(num2);
			int c = a / b;
			out.print(num1 + " / " + num2 + " = " + c);
		} catch(NumberFormatException e) {
			RequestDispatcher dispatcher = request.getRequestDispatcher("tryCatch_error.jsp");
			dispatcher.forward(request, response);
		}
	%>
</body>
</html>
파일명 : tryCatch_error.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>예외 처리</title>
</head>
<body>
	<!-- try-catch 문으로 오류 페이지 출력하기 -->
	<p>잘못된 데이터가 입력되었습니다.</p>
	<p><%= "숫자1 : " + request.getParameter("num1") %></p>
	<p><%= "숫자2 : " + request.getParameter("num2") %></p>
</body>
</html>

잘못된 데이터를 입력해 제출하면 try문에서 예외가 발생해 catch 문에서 해당 예외를 처리한다.
catch문에서 RequestDispatcher 객체를 생성해 forward() 메서드를 사용하여 tryCatch_error.jsp 페이지로 제어를 전달한다.
이 때 원래의 요청 객체와 응답 객체를 함께 가지고 이동하므로 tryCatch_error.jsp 페이지에서 request.getParameter() 메서드를 사용하여 exception_process.jsp 가 요청받은 파라미터를 사용할 수 있다.

📌 필터

필터(filter)란?
클라이언트와 서버 사이에서 요청(request)과 응답(response) 처리 전에 해당 객체를 먼저 받아 필요한 작업을 처리하는 것


Request 필터 : 사용자 인증, 로그 파일 작성 등
Response 필터 : 응답 결과 데이터 압축, 응답 결과에 내용 추가/수정 등

📝 필터 만들어 적용하기

💫 Step 1. 필터로 사용할 클래스 생성

필터를 생성하려면 필요한 기능을 자바 클래스로 작성해야 하고, Filter 인터페이스를 반드시 구현해야 한다.

Filter 인터페이스의 메서드 (오버라이딩 필수)

init() : 필터 초기화 (JSP 컨테이너가 초기화 작업을 할 때 한번만 실행됨)
doFilter() : 필터가 수행하는 내용
destroy() : 필터 종료 전 실행하는 내용

💫 Step 2. web.xml 파일에 필터 설정

어떤 필터를 어떤 리소스에 적용할지 JSP 컨테이너에 알려주기 위해 web.xml에 내용 작성
<filter> : 필터 이름과 클래스명, 매개변수(파라미터) 값 설정
<filter-mapping> : 필터 이름과 적용할 URL 설정
여러 개의 필터가 설정되어 있으면 선언된 순서대로 실행함


📝 폼에서 전달된 파라미터를 필터로 처리하기

이름을 입력받을 폼 페이지 작성

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>필터 사용</title>
</head>
<body>
	<form method="post" action="filter01_process.jsp">
		<p>이름 : <input type="text" name="name"></p>
		<p><input type="submit" value="전송"></p>
	</form>
</body>
</html>
필터 클래스 작성

package filter;

import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;

public class AuthenFilter implements Filter {

	@Override
	public void init(FilterConfig filterConfig) throws ServletException {
		System.out.println("Filter01 초기화...");
	}
	
	@Override
	public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain)
			throws IOException, ServletException {
		System.out.println("Filter01.jsp 수행...");
        request.setCharacterEncoding("UTF-8");
		String name = request.getParameter("name");
		
		if (name == null || name.equals("")) {
        	// 응답할 페이지에 내용을 작성하기 위해 사용
			response.setCharacterEncoding("UTF-8");
			response.setContentType("text/html; charset=UTF-8");
            PrintWriter writer = response.getWriter(); 
			String message = "입력된 name값이 null입니다.";
			writer.println(message);
            
			return; // 필터 수행 내용 끝내기
		}
		chain.doFilter(request, response); // 다음 필터에 전달
	}
	
	@Override
	public void destroy() {
		System.out.println("Filter01 해제...");
	}

}
web.xml 의 <web-app></web-app> 태그 내에 해당 코드 추가

<filter>
  	<filter-name>Filter01</filter-name>
  	<filter-class>filter.AuthenFilter</filter-class>
  </filter>
  <filter-mapping>
  	<filter-name>Filter01</filter-name>
  	<url-pattern>/filter/filter01_process.jsp</url-pattern>
  </filter-mapping>
파일명 : filter01_process.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>필터 사용</title>
</head>
<body>
	<!-- 이 페이지 내용이 실행되기 전에 Filter01 이 먼저 실행됨 -->
	<%
		String name = request.getParameter("name");
	%>
	<p>입력된 값 : <%= name %></p>
</body>
</html>

💻 실행 결과

제출 시 입력값이 없으면 메세지가 출력된다.

profile
🌱

0개의 댓글