본문 바로가기

JAVA/JSP

[JSP] JSP 캐릭터셋 정리

728x90

 

JSP 코드에 들어가는 인코딩 문장들이 헷갈리고 궁금해져서 삽질해가면서 알아가보았다.

 

페이지 상단의 지시자부터 살펴보자

<%@ page language="java" contentType="text/html; charset=UTF-8"  pageEncoding="UTF-8"%>

 

우선 contentType이란?

클라이언트에 자원을 보낼 때 HTTP 헤더를 통해 페이지에 대한 세부정보(소프트웨어 타입, 시간, 프로토콜 등)를 전송함

여기서 charset =UTF-8 을 통해 웹브라우저가 어떤 캐릭터셋으로 페이지를 받을지 선택한다.

 

pageEncoding은 JSP페이지가 어떤 캐릭터셋으로 작성됐는지를 표기한다.

 

요약

<%@ page language="java" contentType="text/html; charset=UTF-8"  pageEncoding="MS949"%>
 jsp파일은 MS949로 작성되었으며 브라우저는 UTF-8로 받게될 것이다.

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
<%@ page language="java" contentType="text/html; charset=utf-8"
    pageEncoding="ms949"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
 
<%request.setCharacterEncoding("utf-8"); %>
 
<jsp:include page="include.jsp">
<jsp:param value="길동" name="name"/>
</jsp:include>
 
</body>
</html>
cs

include.jsp"</span><span

charset을 utf-8로 pageEncoing을 ms949로 세팅하고 출력하니

정상적으로 출력된다.

 

하지만 반대로 

1
2
<%@ page language="java" contentType="text/html; charset=ms949"
    pageEncoding="utf-8"%>
cs

 

charset을 ms949로 세팅하고 돌려보았다.

글자가 깨진다.

 

한마디로 jsp파일의 캐릭터셋을 담당하는 pageEncoding는 jsp소스파일을 다른 환경에서 열람 등 할 때 소스의 상태를 관리하는 문장이고

 

우리가 소스를 실행시킬 때 웹브라우저의 출력의 글자깨짐을 막기 위해서는 charset을 건드려주어야 한다.

 

charset이 utf-8로 해야 정상출력되는걸 보아 크롬은 캐릭터셋이 UTF-8로 default세팅 되어있는걸 알 수 있다.

 

테스트 겸 익스플로러로 인코딩 속성을 UTF-8에서 한국어 방식인 ms949로 바꿔주었더니 크롬에선 깨져있던 페이지가 정상적으로 출력된다.

 

(크롬에서는 인코딩속성 변경하려면 이상한 플러그인 설치해야하더라;)

 

 

 

다음으로 jsp파일 지시어 다음에 헤드에 들어오는 이 UTF-8은 html의 페이징 캐릭터 셋이다.

<%@ pageEncoding%>는 jsp인코딩인데

본문의 소스를 굳이 2번씩이나 인코딩해주어야 하나 싶다.

 

+ 찾아보니 jsp파일은 서블릿 변환되어 소스파일을 읽으므로 html 캐릭터셋보다 jsp캐릭터셋을 더 우선한다.

그러므로 지시자에 charset이 선언되어 있으면 html부문의 meta charset은 무시된다.


소스파일 body에 사용되는 charset 문장은 아래와 같다.

 

  • request.setCharacterEncoding("UTF-8");
  • response.setCharacterEncoding("UTF-8");
  • response.setContentType("text/html; charset=utf-8");

하나씩 기능을 알아보자.

 

1) request.setCharacterEncoding("UTF-8");

jsp 혹은 html에서 작성된 폼 데이터를 전송할 때 UTF-8방식으로 전송하겠다는 뜻이다.

 

하지만 GET방식은 URL을 통해( UTF-8 세팅이 되어있는 톰캣을 거침) 캐릭터 셋 처리를 하기 때문에 톰캣이 세팅된 대로 처리된다.

 

html 소스

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
 
<form name="form" action="print2.jsp" method="post">
- 이름 : <input type ="text" name="name"/>
<input type ="submit" value="전송"/>
</form>
 
</body>
</html>
cs

 

jsp 소스

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
<%
    String name = request.getParameter("name");
%>
이름은 <%= name %> 이다.
 
 
</body>
</html>
cs

 

아주 간단한 폼을 만들어 실험해보면

폼의 속성을 post로 했을 땐

 

글자가 깨지지만

 

get으로 수정 후

 

잘 출력된다.

 

post방식에서도 출력하기 위해서는 폼에서 넘어오는 값을 utf-8로 받아야한다.

 

1
2
3
4
5
6
7
8
<body>
<%
    request.setCharacterEncoding("UTF-8");
    String name = request.getParameter("name");
 
%>
이름은 <%= name %> 이다.
</body>
cs

jsp파일에 request setchar 문장을 삽입해주면

post방식으로도 잘 출력된다.

한마디로 넘어오는 캐릭터셋을 UTF-8로 요청한다는 

 

 

2)response.setContentType("text/html;charset=utf-8")

브라우저에게 출력형식을 UTF-8로 표현하겠다고 선언하는 문장이다.

 

인자를 받을 서블릿 코드를 적당히 작성하자

1
2
3
4
5
6
        PrintWriter out = response.getWriter();
        
        String name = request.getParameter("name");
        request.setAttribute("name", name);
        System.out.println(name);
        out.println("이름 =  " + name);
cs

 

그대로 html폼에 연결하여 '길동' 값을 넣고 실행하면 위와 같이 페이지 인코딩과 인자 둘다 깨지게된다.

이 때 response.setCharacterEncoding을 삽입해보자.

1
2
3
4
5
6
7
8
        response.setContentType("text/html;charset=utf-8");
        String name = request.getParameter("name");
        PrintWriter out = response.getWriter();
        
        
        request.setAttribute("name", name);
        System.out.println(name);    
        out.println("이름 =  " + name);
cs

 

 

 

소스의 한글은 제대로 출력되나 인자로 넘어오는 한글은 깨진다.

 

 

3. request.setCharacterEncoding("utf-8");

서블릿으로 넘어오는 파라미터를 utf-8로 출력한다는 문장

 

 

1
2
3
4
5
6
7
8
9
10
11
12
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        request.setCharacterEncoding("utf-8");
        response.setContentType("text/html;charset=utf-8");
        String name = request.getParameter("name");
        PrintWriter out = response.getWriter();
        
        
        request.setAttribute("name", name);
        System.out.println(name);    
        out.println("이름 =  " + name);
    
    }
cs

request 인코딩 메소드 실행하면

 

 

정상적으로 출력된다.

 

두 메소드를 정리하자면

response.setContentType("text/html;charset=utf-8");는 브라우저에 전송되는 데이터를 인코딩하는것

request.setCharacterEncoding("utf-8"); 는 파라메터(인자)로 전송되는 데이터를 인코딩하는것이다.

 

 

 

 

1
2
3
4
5
6
7
8
9
10
11
12
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        request.setCharacterEncoding("utf-8");
        response.setContentType("text/html;charset=utf-8");
        String name = request.getParameter("name");
        PrintWriter out = response.getWriter();
        
        
        request.setAttribute("name", name);
        System.out.println(name);    
        out.println("이름 =  " + name);
    
    }
cs

만약 request.setCharacterEncoding메소드를 response.setCharacterEncoding("utf-8");로 바꾼다면 역시나 깨지게 된다.

 

 

요약

pageEncoding="utf-8"%

문서를 어떤 캐릭터 셋으로 작성할지 정하는 것

 

response.setContentType("text/html;charset=utf-8")

contenttype 이 메소드는 브라우저에 표현할 때 어떤 캐릭터 셋을 사용할지 정하는 것

 

request.setCharacterEncoding

이 메소드는 서블릿에 사용된다. 서버측으로 데이터를 '요청'하게 되는데 이 때문에 request 객체를 사용하게 된다.

 

response.setCharacterEncoding

이 메소드는 jsp출력에 사용된다. 즉 서버에서 브라우저로 데이터를 '응답'할 때 사용하는데 이 때문에 response 객첼르 사용한다.