반응형

JSP란?
Java Server Pages, 즉 JSP는 다이나믹 HTML를 생성하기 위한 자바진영의 기술입니다.

JSP는 마이크로소프트의 ASP에 대항하기 위한 자바진영의 기술로, 서블릿의 가지고 있는 디자인과 코드의 분리의 어려움을 개선한 기술입니다.
JSP 문서의 확장자는 반드시 .jsp 이어야 합니다.
다음 코드는 간단한 JSP파일의 예입니다.


<html>
<body>
<% out.println("Hello JSP Reader"); %>
</body>
</html>

보기에는 단순한 HTML 파일 같지만 사실 자바 코드를 포함하고 있습니다.
이제 이 파일을 클라이언트의 웹 브라우저에서 보기 위해 hello.jsp 로 우리가 만든 /bbs 디렉토리에 옮겨 놓으면 됩니다.


클라이언트가 hello.jsp를 요청하면, 서버는 .jsp 확장자를 인식하고 이것이 특별한 핸들링이 필요하다는 것을 판단하여 서블릿 컨테이너에게 이 파일을 보내게 됩니다. (이것은 웹서버와 PHP 파서와의 관계와 마찬가지입니다)


그러면 JSP엔진은 .jsp 파일을 받아서 이를 서블릿으로 변환합니다.
변환된 서블릿은 톰캣의 경우 <TOMCAT_HOME>/work 에서 확인할 수 있습니다.

 

위의 간단한 예제도 결국은 서블릿으로 변환됩니다.
hello.jsp 가 처음으로 불리워진다면 이 파일은 서블릿으로 변환되고 컴파일된 후에 상주 메모리에 로딩됩니다.


그런 후에 해당하는 출력내용을 요청한 클라이언트에게 보내게 됩니다.


이후 똑같은 요청이 들어오면, 서블릿 엔진은 원본 .jsp 소스가 변경되었는지를 체크합니다.

그리고 객체가 이미 로딩되었는지 확인합니다. 로딩이 되었다면 로딩된 객체가 서비스하고 로딩되지 않았다면 메모리에 로딩시킵니다.

소스가 변경되었다면 JSP엔진은 JSP소스를 다시 파싱하여 서블릿으로 변환합니다.


다음 그림은 JSP 소스의 파싱 과정을 나타낸다.

최초의 클라이어트가 접속하여 서비스를 요청할 때 컨테이너는 JSP 페이지가 서블릿으로 변환하고 서블릿을 컴파일하여 요청에 응답합니다.

일단 서블릿이 요청에 응답하면 메모리에 로딩되어 있는 상태로 다음 클라이언트의 요청을 기다리게 됩니다.

사용자 삽입 이미지

※ JSP도 서블릿 기반의 기술입니다.
따라서 JSP는 서블릿의 자원과 기능을 가집니다.

JSP Directives

이것은 JSP페이지의 전반적인 정보를 서블릿 엔진에게 제공합니다.
JSP 스펙에 의해 현재에 가능한 지시어는
page, include, taglib 입니다.

page Directive

용법 : <%@ page {attribute="value"} %>

 

페이지 지시어의 속성 설명

language="scriptLanguage"

페이지를 컴파일할 서버측 언어가 무엇인지 기술

extend="className"

페이지가 상속한 부모클래스를 정의

import="importList"

페이지가 import하는 자바팩키지 리스트 기술 (,로 구분)

session="true|false"

페이지에 session 데이터가 이용되는지의 여부를 결정

(디폴트값:true)

buffer="none|size in kb"

출력 스트림의 버퍼크기를 결정(디폴트값:8kb)

autoFlush="true|false"

출력버퍼가 자동적으로 비워지는가 또는 버퍼가 차면 익셉션을 발생할것인가 여부를 결정 (디폴트값:true)

isThreadSafe="true|false"

JSP엔진에게 이 페이지가 일시에 다중으로 서비스할 수 있는가의 여부를 알림

(디폴트값은 true, 만약 이 값이 false로 셋팅되었다면

SingleThreadModel 로 페이지가 작동합니다.)

info="text"

JSP페이지에 관한 정보를 나타낸다.

Servlet.getServletInfo()메소드를 이용해 접근가능

errorPage="error_uri"

JSP 익셉션을 다루는 에러 페이지의 상대경로를 나타냄

isErrorPage="true|false"

페이지가 에러핸들링하는 페이지인가를 기술(디폴트값:false)

contentType="ctinfo"        

클라이언트로 보내질 response의 MIME타입과 캐릭터셋


※ 디폴트 값이 적용되므로 개발자는 이 속성을 모두를 정의해 줄 필요가 없습니다.

java.util팩키지를 import하는 페이지 지시어 예


<%@ page import="java.util.*" %>

include Directive


inlcude 지시어는 JSP 변환때에 텍스트나 소스를 삽입하기 위해 사용합니다.


용법 : <%@ include file="relativeURLspec" %>

삽입되는 문서의 포맷을 html이거나 jsp이거나 상관없지만 웹 애플리케이션내에 존재해야 합니다.

예) <%@ include file="header.jsp" %> 상대경로 사용

※ include 지시어는 변환때 한번만 사용됩니다.
따라서 삽입되는 소스파일이 변경될때는 JSP/Servlet엔진이 재시작되기 전까지는 반영되지 않습니다.

taglib Directive


taglib 지시어는 JSP페이지가 커스텀 태그 라이브러리를 이용함을 기술합니다.
커스텀 태그 라이브러리는 각각의 커스텀 태그 집합을 구별하는 prefix와 uri로 유일하게 구별됩니다.

용법 : <%@ taglib uri="tagLibraryURI" prefix="tagPrefix" %>

태그라이브러리 지시어 속성


uri               커스텀태그 라이브러리를 고유하게 이름짓는 URI 참조
prefix            커스텀 태그 라이브러리를 구별하는데 쓰이는 Prefix 정의


 


Scripting


Scripting은 HTML페이지에 자바코드 조각을 바로 삽입하기 위해 사용합니다.
Scripting에는 Declarations, Exceptions, Scriplets 3가지가 있습니다.
이들 각각은 서블릿의 적절한 위치에서 변화되어 놓이게 됩니다.

Declarations


Declarations는 자바 변수와 메소드를 JSP페이지내에서 선언하기 위해선 사용됩니다.

JSP Declarations는 JSP페이지가 첫번째로 로딩될때 초기화되고 그 후에 같은 페이지내의
다른 Declarations, expressions, scriptlets에게 이용되어 진다.

용법 :
<%! declaration %>

변수 선언 예   : <%! String name = new String("BOB") %>
메소드 선언 예 : <%! public String getName() { return name; } %>

Declarations는 서블릿으로 변환될때 서블릿 클래스의 선언부분에 위치하게 됩니다.

 

Expressions


JSP Expressions는 컨테이너에 의해 결과값(문자열)으로 바뀌는 JSP 컴포넌트입니다.
JSP Expressions는 request타임에 .jsp 파일내에서 컨테이너에 의해 변환되어 삽입됩니다.
만약 결과값이 문자열로 변환되지 않는다면 번역시 에러가 발생합니다.
번역시 문자열이 검출되지 않는다면 ClassCastException 익셉션이 request타임에 발생합니다.
용법 :
<%=expression %>
) Hello <%= getName() %>

Scriptlets


Scriptlets는 모든 JSP 요소를 가져올 수 있는 JSP컴포넌트입니다.
이들은 request타임에 실행됩니다.

용법 :
<% scriptlets source %>

Scriptlets를 가지고 있는 페이지를 처음 요청하면 JSP는 서블릿코드로 변환되고 컴파일되고 상주메모리에 로딩됩니다.
<%...%>로 표현되는 Scriptlets는 서블릿의 service() 메소드내에 위치하게 됩니다.

JSP Error 핸들링

JSP 아키텍처는 오로지 에러만을 다룰 수 있는 JSP페이지로서 에러 핸들링의 해법을 제시합니다.
에러는 주로 런타임 에러가 대부분인데 이것은 JSP 바디안 이거나 또는 JSP 바디안 에서 호출하는 어떤 다른 객체에서 발생합니다.


request타임 에러는 호출한 JSP의 몸체에서 잡을 수 있고 또한 다룰 수 있는 에러가 던져졌을 때 발생합니다.

호출한 JSP의 몸체에서 다룰 수 없는 익셉션의 경우는 잡혀지지 않은 익셉션과 함께 클라이언트 request를 에러 페이지로 전송합니다.

JSP Error 페이지 만들기

JSP Error 페이지를 만드는 것은 간단하다.
기본적인 JSP페이지를 만들고 컨테이너에게 이 페이지가 에러 페이지임을 알리면 됩니다.
이것은 앞서 언급한 page Directives의 isErrorPage를 셋팅하면 됩니다.
다음은 에러페이지의 예입니다.

*** errorpage.jsp ***


<html>
<body>
<%@ page isErrorPage="true" %>
Bob there has been an error : <%= exception.getMessage() %> has been reported.
</body>
</html>

<설명>
<%@ page isErrorPage="true" %>
위 지시자는 이 페이지가 에러 페이지라는 것을 컨테이너에게 알리는 역활을 합니다.

<%= exception.getMessage() %>


는 에러페이지로 전달되어 온 익셉션의 에러 메시지를 출력하기 위한 부분입니다.
이때 exception이라는 내장객체를 사용합니다.

JSP Error 페이지 사용법


에러 페이지가 어떻게 작동하는지 알아보기 위해 잡히지 않는 익셉션을 발생시키는 간단한
JSP페이지를 만들어봅시다.

*** testerror.jsp ***

<%@ page errorPage="errorpage.jsp" %>
<%
   if(true){
      //Just throw an exception
      throw new Exception("An uncaght Exception");
   }
%>

에러페이지를 errorpage.jsp로 셋팅했다.

이렇듯 JSP페이지에게 에러페이지를 알리는 방법은 JSP페이지의 page directive에서
errorPage속성값을 정해주는 것입니다.
속성값에서 에러페이지의 위치는 페이지의 상대경로입니다.

이 예제을 실행해보기 위해서는 testerror.jsp 와 errorpage.jsp을
<TOMCAT_HOME>/webapps/bbs/에 위치시키고 testerror.jsp를 방문합니다.

Implicit Objects ( 내장 객체 )

내장 객체는 JSP문서내에서 이용되는 객체인데 특별히 레퍼런스를 얻기 위한 작업 없이 바로 사용할 수 있는 객체를 말합니다.

out

 

javax.servlet.jsp.JspWriter클래스의 인스턴스를 나타냅니다.
데이터를 응답 스트림으로 작성하는데 사용합니다.
이 객체의 일반적인 메소드는 out.println()입니다.
 사용예


*** out.jsp ***


<%@ page errorPage="errorpage.jsp" %>
<html><head><title>Use Out</title></head>
<body>
<%
   //Print a simple message using the implicit out object.
   out.println("<b> Hello Bob! </b>");
%>

</body></html>

request

 

javax.servlet.http.HttpServletRequest 인터페이스의 인스턴스
요청 파라미터나 헤더와 같은 사용자가 요청한 유용한 정보에 대해 접근할 수 있습니다.
request 객체는 모든 HTTP요청과 관련되어 있습니다.
이 객체는 request의 파라미터를 구하는데 일반적으로 사용되는데
getParamter()메소드를 사용함으로써 파라미터의 값을

리턴받습니다.

예)

*** request.jsp ***

<%@ page errorPage="errorpage.jsp" %>
<html>
<head>
   <title>UseRequest</title>
</head>
<body>
<%
   out.println("<b>Welcome: " + request.getParameter("user") + "</b>");
%>
</body>
</html>


실행하려면 다음 URL을 방문합니다. http://localhost/bbs/request.jsp?user=kim



response


javax.servlet.http.HttpServletResponse 인터페이스의 인스턴스입니다.

사용자에게 리턴할 현재 응답을 나타낸다.
하지만 대부분의 HTML 출력은 out객체를 이용합니다.


pageContext

 

jsp범위 내에서 이용 가능한 모든 자원 및 현재의 요청, 응답, ServletContext,

HttpSession, ServletConfig 같은 페이지 속성들에 접근할 수 있는 방법을 제공합니다.

pageContext 객체는 내장 객체를 접근할 수 있는 방법을 제공합니다.

session

session 객체는 javax.servlet.http.HttpSession 객체를 나타냅니다.
세션 데이타를 읽고 저장하는 데 사용됩니다.
 
session 객체의 사용예
*** session.jsp ***


<html> <lhead> <title>Session Example </title> </head>
<body>
<%
   //get a referece to the current count from the session
   Integer count = (Integer)session.getAttribute("COUNT");

   if(count==null){
      //If the count was not found, create one
      count = new Integer(1);
      //and add it to the HttpSession
      session.setAttribute("COUNT",count);
   } else {
      //Otherwise increment the value
      count = new Integer(count.intValue() +1);
      session.setAttribute("COUNT",count);
   }
   out.println("<b>This page has been accessed: " + count + " times.</b>");
%>
</body> </html>

이 예제를 사용하기 위해서는 session.jsp 파일을
<TOMCAT_HOME>/webapps/mnd에 복사하고 http://localhost/bbs/session.jsp 를 방문합니다.
리로드 버튼을 눌러 결과를 확인합니다.

application


application 객체는 javax.servlet.ServletContext 나타낸다.

이 객체는 주로 웹 컴포넌트가 공유할 수 있도록 ServletContext에 저장되어 있는 객체를 접근하기 위해 사용됩니다.


config


이 객체는 ServletConfig의 레퍼런스를 가지고 있습니다.
ServletConfig는 JSP/Servlet엔진의 관한 설정 정보를 담고 있습니다.
초기화 파라미터들에 접근하기위해 사용합니다.


page


이 객체는 현재 JSP페이지의 레퍼런스를 가지고 있습니다.
jsp페이지의 페이지 구현 클래스 인스턴스를 참조하며 Object형으로 선언되어 있습니다.
page변수는 스크립팅 엘리먼트들 안에서 가끔 사용되며, 단순히 jsp페이지와 구현 서블릿 사이의
연결 역할을 합니다.
 
exception


JSP페이지에서 발생한 잡히지 않은 익셉션에 접근을 제공하는 객체입니다.
이 객체는 page 지시어 중 isErrorPage가 true로 설정한 페이지내에서만 사용이 가능합니다.

, 페이지디렉티브를 이용해서 에러 페이지로 지정한 jsp에서만 유용한 객체입니다.


표준 액션

표준 액션이란 미리 제공된 커스텀 태그라 생각하면 됩니다.
6가지 표준액션이 제공됩니다.

<jsp:useBean>

이 표준액션은 자바빈을 생성하거나 생성된 자바빈을 찾기 위한 액션입니다.
<jsp:useBean>은 매우 유연합니다.


JSP문서내에서 <jsp:useBean>부분에 이르면 우선 같은 scope와 ID를 사용하는 객체를 찾습니다.
만약 찾는것에 실패하면 scope와 ID와 관련이 있는 객체를 생성하기 위해 시도합니다.

신택스


<jsp:useBean id="name" scope="page|request|session|application" typeSpec>
body
</jsp:useBean>

typeSpec :: =class="className" |
       class="className" type="typeName" |
       type="typeName" class="className" |
       beanName="beanName" type="typeName" |
       type="typeName" beanName="beanName" |
       type="typeName"

<jsp:useBean>의 속성 설명
id : 특정 scope 내에서 객체의 인스턴스와 관련되어 있는 키
scope : 참조되는 객체의 라이프 page | request | session | application

class : 객체의 구현을 정의하는 클래스
beanName : 자바빈의 레퍼런스
type : 정의된 변수의 타입(정의되지 않으면 class의 속성값과 같습니다)

<jsp:setProperty>

이 액션은 자바빈의 속성값을 셋팅하는 데 쓰입니다.

신택스 : <jsp:setProperty name="beanName" propexpr />
name 속성은 빈의 이름을 나타낸다.

propexpr

property="*" |
property="propertyName" |
property="propertyName" param="parameterName" |
property="propertyName" value="propertyValue"

<jsp:setProperty> 액션의 속성 설명

name  

<jsp:useBean>에서나 다른 액션에서 정의된 인스턴스의 이름


property  

셋팅을 원하는 곳의 속성
만약 propertyName에다가 * 라고 셋팅하면 ServletRequest로부터 차례대로 전달받은 파라미터로 모든 속성값을 세팅하게
됩니다.
만일 해당 파라미터가 비어있습니다면 수정되지 않는다.


param    

셋팅하기를 원하는 파라미터의 이름

value      

빈의 속성에 대응하는 값

<jsp:getProperty>

빈의 속성값을 가져와서 스트림으로 변환하고 이것을 output 스트림에 두는 액션
신택스    <jsp:getProperty name="name" property="propertyName" />

<jsp:getProperty> : 표준 액션 속성 설명
name   : 빈 인스턴스의 이름
property  : 얻고자 하는 빈 인스턴스의 속성값

<jsp:param>

이 액션은 표준 액션, <jsp:include>,<jsp:forward>,<jsp:plugin>에 파람값을 전달할때 이용합니다.

신택스 : <jsp:param name="name" value="value" />

<jsp:param> 의 속성 설명
name : 파리미터의 이름
value : 파리미터의 값

<jsp:include>


이 액션은 JSP페이지에 정적 또는 다이나믹 웹 컴포넌트를 추가할때 사용합니다.

신택스
<jsp:include page="urlSpec" flush="true">
   <jsp:param ... />
</jsp:include>

<jsp:include> 의 속성 설명
page :  인클루드 되는 소스의 상대경로
flush :  버퍼가 비워지는 여부

※ include 지시어와 include 표준 액션과의 차이점
지시어는 한번만 번역타임에 해석되지만 표준액션의 경우는 매 request타임마다 해석됩니다.
따라서 지시어를 사용한 인클루드는 인클루드되는 파일의 변화는 톰캣이 재시동되지 않으면 반영되지 않습니다.


<jsp:forward>

이 액션은 JSP엔진이 실행중에 request를 다른 자원(정적 문서,서블릿, JSP)에게 넘기는 것을 가능하게 합니다.
이 액션에서도 <jsp:param>가 쓰일 수 있는데 이는 포워딩할 대상자원에게 전달할 파라미터를 지정하기 위해 쓰입니다.

신택스   
<jsp:forward page="relativeURL">
   <jsp:param .../>
</jsp:forward>

단일 속성 page는 포워딩할 대상자원을 상대주소로 나타낸 값입니다.

<jsp:plugin>

이 액션은 다운로드나 애플릿,자바빈의 실행을 일으키는 HTML 코드를 생성하는데 사용됩니다.
이 액션은 한번 해석되어 <object> 나 <embed>로 바뀝니다.
속성은 바뀌는 코드에 표현을 위한 설정데이터로 제공됩니다.

신택스
<jsp:plugin type="pluginType" code="classFile" codebase="relativeURLpath">
   <jsp:params>
   </jsp:params>
</jsp:plugin>

<jsp:plugin>의 속성 설명
type : 인클루드할 플러그인 타입 예를 들면 applet
code : 플러그인이 실행할 클래스의 이름
codebase : 클래스의 절대 또는 상대경로



서블릿컨텍스트와 웹 애플리케이션의 관계

 

서블릿컨텍스트와 웹 애플리케이션과의 관계에 대해 알기 전에 먼저 서블릿컨텍스트가 무엇인지 부터 알아야 합니다.
서블릿컨텍스트(ServletContext)는 javax.servlet 팩키지에 속하는 객체입니다.

이것은 웹 애플리케이션의 서브 사이드 컴포넌트와 서블릿 컨테이너와의 통신을 담당하는 메소드 집합을 정의합니다.

서블릿컨텍스트의 가장 일반적인 사용중 하나는, 웹 애플리케이션의 서버 사이드 컴포넌트들 모두에게 이용될 수 있는 객체를 위한 저장소로 이용되는 것입니다.
서블릿컨텍스트에 저장된 객체는 웹 애플리케이션의 일생동안 존재합니다.
4개의 서블릿컨텍스트의 메소드는 공유메모리기능를 제공하기 위해 쓰입니다.

다음은 각각의 메소드에 관한 설명입니다.

setAttribute(java.lang.String name,java.lang.Object object)


첫번째 파라미터값인 이름으로 객체를 바인딩하고 객체를 서블릿컨텍스트에 저장합니다.
만약 특정 이름이 이미 사용중이라면 기존의 이름으로 바인딩된 속성을 지우고 새로운 객체를 이 이름으로 바인딩합니다.

getAttribute(java.lang.String name)


첫번째 파라미터값을 이름으로 참조하는 객체를 반환합니다.
만약 주어진 이름으로 바인된 속성이 없다면 널을 반환합니다.

getAttributeNames()
서블릿컨텍스트에 저장된 속성이름을 Enumeration 타입으로 반환합니다.

웹 애플리케이션과 서블릿컨텍스트의 관계


우리는 이미 <TOMCAT_HOME>/conf/server.xml 파일에 새로운 Context를 추가했습니다. (톰캣 admin 툴을 이용해서).
이 작업을 하면 웹 애플리케이션을 생성한 것입니다.
웹 애플리케이션을 추가함과 동시에 새로운 서블릿컨텍스트를 또한 만든 것입니다.
이것이 웹 애플리케이션과 서블릿컨텍스트의 관계입니다.
모든 웹 애플리케이션마다 단 하나의 서블릿컨텍스트가 있습니다.
이는 서블릿 스펙에 의해 요구되어지고 모든 서블릿엔진에 의해 수행됩니다.

웹 애플리케이션이 웹 애플리케이션 컴포넌트에 어떻게 영향을 미치는지의 예

실제로 서블릿컨텍스트와 웹 애플리케이션과의 관계를 이해하기 위해,
우리는 이미 만든 /bbs 웹 애플리케이션을 외에 /bbs2 라는 웹 애플리케이션을 추가합니다.(톰캣 admin 툴 이용)
그리고 각각의 웹 애플리케이션에 아래와 같은 2개의 웹컴포넌트를 각각 배치합니다.


첫번째 웹 컴포넌트 서블릿

*** ContextText.java ***

 

package example;

import javax.servlet.*;

import javax.servlet.http.*;

import java.io.*;

import java.util.*;

 

public class ContextTest extends HttpServlet{

             private static final String CONTENT_TYPE="text/html;charset=euc-kr";

             public void init() throws ServletException {

             }

             public void doGet(HttpServletRequest request,HttpServletResponse response)

                           throws ServletException,IOException{

 

                           doPost(request,response);

             }

             public void doPost(HttpServletRequest request,HttpServletResponse response)

                           throws ServletException,IOException{

 

                           // ServletContext 레퍼런스를 얻는다.

                           ServletContext context=getServletContext();

                           // ServletContext로부터 count 속성값을 얻기를 시도합니다.

                           Integer count=(Integer)context.getAttribute("count");

                           // 만약 count 속성이 없다면 만든다.

                           // count 속성 초기값은 0 입니다.

                           if(count==null){

                                        count=new Integer(0);

                                        context.setAttribute("count",new Integer(0));

                           }

 

                           response.setContentType(CONTENT_TYPE);

                           PrintWriter out=response.getWriter();

                           out.println("<html>");

                           out.println("<head><title>ContextTest</title></head>");

                           out.println("<body>");

                           // count 속성값의 현재값을 출력합니다.

                           out.println("<p>현재 COUNT 는 : "+count+".</p>");

                           out.println("</body></html>");

                           // doPost메소드가 불릴때마다 count 속성값을 1씩 증가시킨다.

                           count=new Integer(count.intValue()+1);

                           // ServletContext에 증가한 count 속성을 저장합니다.

                           context.setAttribute("count",count);

             }

             public void destory(){

             }

}

 


코드 설명


1. getServletContext()메소드를 이용해서 ServletContext의 레퍼런스를 얻습니다.


ServletContext context = getServletContext();

2. 서블릿컨텍스트의 레퍼런스를 얻었다면 서블릿컨텍스트로부터 count 속성값을 얻고자 시도합니다.

이때 getAttribute()메소드를 사용합니다.

Integer count = (Integer)context.getAttribute("count");

3. 서블릿컨텍스트에 count라는 속성이 있는지 조사하고 만일 그런 속성이 존재하지 않는다면 만들고 서블릿컨텍스트에 추가합니다.

이때 setAttribute()메소드를 사용합니다.

if( count == null) {
   count = new Integer(0);
   
context.setAttribute("count",new Integer(0));
}

4. 속성이 발견되었다면 이 값을 출력스트림에 씁니다.


out.println("<p>The current COUNT is : " + count + ".</p>");

5. 서블릿컨텍스트의 속성값을 증가시키고 이 값을 서블릿컨텍스트에 추가합니다.

count = new Integer(count.intValue() + 1);

context.setAttribute("count", count);

서블릿을 2개의 웹 애플리케이션에 배치합니다.
위 서블릿 코드를 bbs/WEB-INF/classes와 bbs2/WEB-INF/classes 에 위치시킨후

javac -d . ContextTest.java


라는 명령어로 컴파일하고


http://localhost/bbs/servlet/example.ContextTest

http://localhost/bbs2/servlet/example.ContextTest


를 방문해 확인합니다.

2번째 웹컴포넌트 JSP페이지


파일위치 : /bbs/example/ , /bbs2/example/


***
ContextTest.jsp ***


<%@ page contentType="text/html;charset=euc-kr" %>

<HTML><head><title>ContextTest</title></head><body>

<h1>

<%

             // count 속성을 얻기를 시도합니다.

             Integer count=(Integer)application.getAttribute("count");

             // 만약 count 속성이 null이면 하나 만들어서 서블릿컨텍스트에 저장합니다.

             if(count==null){

                           count=new Integer(0);

                           application.setAttribute("count",count);

             }

%>

 

현재 COUNT 는 : <%=count%>

<%

             // count 속성을 1 증가시켜 서블릿컨텍스트에 새로 저장합니다.

             count=new Integer(count.intValue()+1);

             application.setAttribute("count",count);

%>

</h1>

</body></html>


이 파일을 bbs/example 와 bbs2/example 에 복사합니다.
각각의 분리된 웹 애플리케이션이 어떻게 이들 컴포넌트에 영향을 미치는지 확인합니다.
실험을 시작하기 위해 다음 URL를 방문합니다.

http://localhost/bbs/example/ContextTest.jsp

http://localhost/bbs2/example/ContextTest.jsp



Refresh 버튼을 여러번 누르고 count가 증가되는지 확인합니다.
새로운 브라우저를 열고 서블릿을 방문합니다.

http://localhost/bbs/servlet/example.ContextTest

http://localhost/bbs2/servlet/example.ContextTest



출력결과는 ContextTest.jsp 와 같을 것입니다.
count의 값에 주목합니다.


ContextTest.jsp에서보다 1만큼 증가된 값입니다.
이것은 서블릿과 JSP가 같은 서블릿컨텍스트를 공유하고 있습니다는 의미입니다.
서블릿 컨텍스트의 공유메모리 기능입니다. (공동 저장소 기능)
각각 JSP와 서블릿을 방문함으로써 count 객체가 어떻게 공유되는지 알 수 있습니다.

이제 /bbs2/ContextTest.jsp JSP페이지를 새로운 창으로 방문합니다.
http://localhost/bbs2/example/ContextTest.jsp count의 값이 0인 결과화면을 볼 수 있습니다.
이것이 의미하는 것은 /bbs 웹 애플리케이션이 사용하는 count와 지금의 count는 다르다는 것입니다.
이것이 웹 애플리케이션과 서블릿컨텍스트의 관계입니다.
/bbs2 와 관련이 있는 서블릿 컨텍스트는 이 웹 애플리케이션에 유일합니다.
그리고 다른 웹 애플리케이션 /bbs 안에 있는 웹 컨포넌트에 의해 영향을 받지 않는다는 것입니다.


다시 확인을 위해 /bbs2 의 서블릿을 방문합니다.
http://localhost/bbs2/servlet/example.ContextTest
/bbs2 에 배치된 JSP와 같은 count 레퍼런스를 사용함을 알 수 있습니다

 

JSP 문법에서 꼭 확인해야 할 사항들


1. <%@ page session=true>


Q. page 지시자에서 session 속성은 구체적으로 무엇을 의미하는가?

page 지시자에 session 속성이 false로 되어 있으면 웹 컨테이너에서는 해당 페이지가 session 객체를 생성하지도 못하고 또한 기존의 session 객체에 대한 레퍼런스도 얻을 수도 없습니다.

false로 되어 있는 상태에서 session 객체에 접근하고자 하면 에러가 발생하게 됩니다.

 

2.<jsp:useBean id="name" scope="page|request|session|application"  class=ClassName />


Q. 표준액션의 <jsp:useBean>에서 scope 속성은 무엇을 의미하는가?

scope 속성은 jsp:useBean 속성 중에서 가장 중요한 부분입니다.

일단 이 속성은 자바 빈즈를 객체화시킨 후 어느 범위까지 사용을 할 것인지를 결정하는 것입니다.

Scope 속성으로 지정한 영역의 수명에 따라서 빈 객체는 하나의 페이지가 아니라 여러 페이지에서 소멸하지 않고 참조되기고 합니다.

(예를 들어 scope 속성이 session 으로 설정되었다면 빈 객체는 세션이 종료할 때까지 소멸되지 않고 유지됩니다.)

빈 객체가 생성된 이후 어떤 페이지에서도 참조될 수 없을 때 자동으로 소멸됩니다.

Scope 속성은 기본 값은 page입니다.

scope 속성에는 4개의 값을 지정해 줄 수 있는데 각각의 값에 대해서 정리하면 다음과 같습니다.

 

page : 자바 빈즈가 현재의 JSP 페이지 내에서만 사용 가능하도록 설정할 때

기본 값이므로 특별히 지정하지 않으면 이 옵션이 적용됩니다.

빈 객체의 수명은 한 페이지 내에서만 유지됩니다.

Page 영역으로 생성된 객체는 요청된 페이지 내에서만 유효합니다.

같은 페이지를 요청해도 새로운 빈 객체가 생성됩니다.

페이지의 실행 종료와 함께 빈 객체는 소멸됩니다.

매 페이지마다 새로 생성되므로 객체가 생성자의 초기화 부분을 항상 실행합니다.

Page영역은 한 페이지에서만 유효하므로 <jsp:include> 태그나 <jsp:forward> 태그로 포함된 페이지에서

<jsp:useBean> 태그는 이미 만들어진 빈 객체를 참조하는 것이 아니라 같은 id 속성값을 가진 새로운 객체를 생성하게 됩니다.

또한 <jsp:include> 태그에서 생성한 빈 객체는 원 페이지에서 참조될 수 없습니다.

Page 영역의 빈 객체는 jsp 페이지가 불릴 때마다 먼저 생성된 빈 객체의 상태가 필요하지 않고 새로 생성되어도 되는 경우에 적합하다.

 

request : JSP 페이지는 jsp:forward, jsp:include 태그를 이용해서 다른 JSP 페이지와 함께 사용할 수 있는데 이 값으로 범위를 지정하면 현재의 JSP 페이지와 연결되어 있는 모든 JSP 페이지까지 영향을 미칩니다.

이럴 경우 이 자바 빈즈의 id는 다른 페이지에 동일한 이름의 id가 존재해서는 안됩니다.

반대로 page 속성으로 지정되어 있을 경우에는 현재 페이지에 jsp:forward와 jsp:include가 있을 지라도 해당 페이지까지 영향을 미치지는 않습니다. 즉, 해당 페이지가 원 페이지에서 참조하는 자바 빈즈를 참조하지 못합니다.

또한 request 영역으로 생성된 빈 객체를 request 객체에 저장하여 request 객체에서 찾아서 참조가 가능합니다.

<jsp:include> 태그와 <jsp:forward>태그를 사용하는 경우 같은 request 객체를 사용하게 됩니다.

 

session : 이 값으로 범위를 지정해 놓으면 세션에 유효할 때까지 자바 빈즈의 객체가 유효합니다.

세션이 유지되는 동안 같은 세션에서 호출되는 모든 페이지에서 빈 객체는 소멸되지 않고 유지됩니다.

Session 영역으로 생성된 빈은 session 객체에 저장됩니다.

각 사용자에 대하여 독립적으로 생성되는 session 객체는 세션이 종료될 때까지 호출되는 모든 페이지에서 id 속성으로 구분되는 객체들을 유지하고 사용할 수 있게 해준다.

한가지 주의할 점은 page 지시자에서 session 속성을 false로 해 놓았을 경우에는 이 자바 빈즈 객체는 사용할 수 없게 됩니다.

page,request  scope 속성으로 생성된 빈은 브라우저의 요청에 대하여 결과를 생성하여 돌려준 다음에는 소멸됩니다.

 

application : 이 값은 가장 광범위한 범위를 갖는 값입니다. 이 값으로 범위를 지정하면 모든 JSP 페이지에서 사용할 수 있으며 자바 빈즈 객체는 JSP 엔진을 정지시키거나 다시 시작시킬 때까지 계속 살아 있게 됩니다.

즉, JSP엔진에 의해 소멸되지 않고 유지됩니다.

application scope 속성으로 생성된 빈은 application 내장객체에 저장되어 같은 웹 애플리케이션을 사용하는 모든 사용자에게 사용되어 질 수 있게 됩니다. 이 옵션은 거의 사용되지 않습니다.

 

3. <%@ include file=”상대경로파일명” %> 과 <jsp:include page=”상대경로파일명” /> 의 정확한 차이는?

 

Include 디렉티브의 경우 포함되는 페이지와 현재 jsp 페이지가 합쳐져서 하나의 jsp 페이지(이는 곧 합쳐진 jsp페이지가 서블릿으로 변환됨을 의미)가 되는 반면에 <jsp:include>액션 태그로 포함되는 페이지와 포함하는 페이지가 합쳐지지 않고 그대로 존재하게 됩니다.

<출처:
http://cafe.naver.com/webprogramguide>

+ Recent posts