본문 바로가기
Java Web Programming/3. Servlet

[Servlet] ServletContextListener 개념, 구현 방법 및 예제

by 파프리카_ 2020. 8. 24.
728x90
반응형

ServletContextListener 란?

: 웹 어플리케이션 LifeCycle 발생 시 실행되는 메서드를 가진 객체

 

* ServletContextListener를 사용하는 이유

→ Servlet의 LifeCycle은 Container가 담당한다(init() / service 계열  method / destory() - 객체 생성, 초기화, 서비스, 소멸의 역할을  Container가 함). 이 때, 초기화 단계에서 해야 하는 일들이 있다. 예를 들어, 파일을 직렬화하여 정보를 불러오거나, 초기 설정을 해주어야 한다. 그리고 소멸할 때, 파일을 역직렬화해서 저장(백업) 해놓는 등의 작업이 필요하기 때문에, listner class가 유용하게 사용될 수 있다.

⇒ Servlet/JSP가 들어있는 Web application의 LifeCycle의 event를 관리할 수 있다 ! 

 

 


[ Tool로 생성 방법 ]

src > New > Listener 클릭

 


[ 주요 메서드 ]

  • contextInitialized(ServletContextEvent event)
    - web application 시작 시 한번 생성되는 ServletContext 생성 직후 호출되어 실행되는 메서드

    - 해당 web application 초기화 관련 작업에 이용할 수 있다.
  • contextDestroyed(SevletContextEvent event)
    - web application이 종료 직전에 실행되는 메서드

    - 해당 web application 종료 전에 실행해야 할 작업을 명시하여 이용할 수 있다. (주로 백업같은 작업에 이용됨)

web.xml에 아래와 같이 listener tag가 추가되었는지도 확인해보자 !

  <listener>
    <listener-class>listner.TestListener</listener-class>
  </listener>

 


활용 예제

 

-- step1. EnterServlet에서는 클라이언트로부터 전달받은 name과 address를 이용해

<판교에 사는 아이유님 입장을 환영합니다! > 라는 문구와

<회원입장 명단보기>링크를 부여해 ListServlet으로 이동할 수 있도록 한다.

--step2.ListServlet에서는 입장 명단 전체를 제공한다.

<1. 아이유 판교>

<2. 유인나 서울>

 

1. web.xml의 context-param의 name을 filePath, value를 C:\\kosta203\\member.obj로 명시

2. ServletContextListener를 Implements한 ListListener class의 오버라이딩한 메서드 contextInitialized()에서

해당 filePath가 존재하지 않으면, (file.isfile() or file.exist() ) list 객체를 새로 생성해 ServletContext에 할당하고,

존재하면 list를 역직렬화하여 ServletContext의 SetAttribute("list", list)와 같이 할당한다.

3. ServletContextListener를 implements한 ListListener class의 오버라이딩한 메서드 contextDestroyed()에서,

웹 어플리케이션 종료 직전에 추가된 회원 명단이 있는 list 정봅를 context-param의 filePath의 파일에 직렬화해서 저장한다.

 

 

web.xml

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xmlns="http://java.sun.com/xml/ns/javaee"
	xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
	id="WebApp_ID" version="2.5">
	<display-name>webstudy10-ServletContextListener-Exam</display-name>
	<welcome-file-list>
		<welcome-file>index.html</welcome-file>
		<welcome-file>index.htm</welcome-file>
		<welcome-file>index.jsp</welcome-file>
		<welcome-file>default.html</welcome-file>
		<welcome-file>default.htm</welcome-file>
		<welcome-file>default.jsp</welcome-file>
	</welcome-file-list>
	<servlet>
		<description></description>
		<display-name>EnterServlet</display-name>
		<servlet-name>EnterServlet</servlet-name>
		<servlet-class>step1.EnterServlet</servlet-class>
	</servlet>
	<servlet-mapping>
		<servlet-name>EnterServlet</servlet-name>
		<url-pattern>/EnterServlet</url-pattern>
	</servlet-mapping>
	<servlet>
		<description></description>
		<display-name>ListServlet</display-name>
		<servlet-name>ListServlet</servlet-name>
		<servlet-class>step2.ListServlet</servlet-class>
	</servlet>
	<servlet-mapping>
		<servlet-name>ListServlet</servlet-name>
		<url-pattern>/ListServlet</url-pattern>
	</servlet-mapping>
	<listener>
		<listener-class>listener.ListListener</listener-class>
	</listener>

	<context-param>
		<param-name>filePath</param-name>
		<param-value>C:\\kosta203\\member.obj</param-value>
	</context-param>
</web-app>

 

html

index.html

<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>ServletContextListener 연습</title>
</head>
<body>
<form action = "EnterServlet" method="POST">
	이름<input type="text" name="name" required="required"><br>
	주소<input type="text" name="address" required="required"><br>
	<input type="submit" value="입장">
</form>
</body>
</html>

 

 

Servlet Class

EnterServlet.java

package step1;

import java.io.IOException;
import java.io.PrintWriter;
import java.util.ArrayList;

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

import model.MemberVO;


public class EnterServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
    private ArrayList<MemberVO> list;
    
    //init 단계에서 client에서 받아온 정보 list에 저장하기
    @SuppressWarnings("unchecked")
	@Override
    public void init() throws ServletException {
    	list = (ArrayList<MemberVO>) getServletContext().getAttribute("list");
    }
    
	//doPost method
	protected void doPost(HttpServletRequest request, HttpServletResponse response) 
			throws ServletException, IOException {
		response.setContentType("text/html; charset=utf-8");
		PrintWriter out = response.getWriter();
		request.setCharacterEncoding("utf-8");
		
		String name = request.getParameter("name");
		String address = request.getParameter("address");
		
		//list에 add한다
		list.add(new MemberVO(name, address));
		
		out.println(address+"에 사는 "+name+"님 입장을 환영합니다!<br>");
		out.println("<br>");
		out.println("<a href = ListServlet>회원 입장 명단보기</a>");
		
		out.close();
	}

}

 

 

ServletContextListener Class

ListServlet.java

package step2;

import java.io.IOException;
import java.io.PrintWriter;
import java.util.ArrayList;

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

import model.MemberVO;


public class ListServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
    ArrayList<MemberVO> list;   
	
	//init 단계에서 ServletContext로부터 리스트를 받환받아
	//인스턴스 변수에 할당하기
	@SuppressWarnings("unchecked")
	@Override
	public void init() throws ServletException {
		//getAttribute(name)
		list = (ArrayList<MemberVO>) getServletContext().getAttribute("list");
	}
	
	protected void doGet(HttpServletRequest request, HttpServletResponse response) 
			throws ServletException, IOException {
		response.setContentType("text/html;charset=utf-8");
		PrintWriter out = response.getWriter();
		
		//화면에 출력
		for (int i = 0; i < list.size(); i++) {
			out.println(i+1+"."+list.get(i).getName()+ " "
						+ list.get(i).getAddress() + "<br>");
		}
		
		out.println("<br>");
		//등록 화면 돌아가기
		out.println("<a href=index.html>입장정보 등록으로 이동</a>");
		
		out.close();
	}

}

 

ListListener.java

package listener;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.util.ArrayList;

import javax.servlet.ServletContextEvent;
import javax.servlet.ServletContextListener;

import model.MemberVO;

public class ListListener implements ServletContextListener {

	// contextDestroyed method : WAS 종료 전에 호출되는 메서드
	// 객체 직렬화 : filePath에 list를 직렬화해서 저장
	public void contextDestroyed(ServletContextEvent event) {
		String filePath = event.getServletContext().getInitParameter("filePath");
		
		try {
			ObjectOutputStream oos 
				= new ObjectOutputStream(new FileOutputStream(filePath));
			
			//getAttribute를 통해 가져와서 객체 직렬화
			oos.writeObject(event.getServletContext().getAttribute("list"));
			oos.close();
		} catch (IOException e) {
			e.printStackTrace();
		}
	}

	// contextInitialized method : web application 시작 시에 호출되는 메서드
	// filePath를 확인해서
	// -> 있으면 list를 역직렬화해서 반환받아 ServletContext에 setAttribute()하고
	// -> 없으면 list를 새로 생성해서 ServletContext에 SetAttribute()
	public void contextInitialized(ServletContextEvent event) {
		String filePath = event.getServletContext().getInitParameter("filePath");
		File file = new File(filePath);

		if (file.isFile()) {
			try {
				ObjectInputStream ois 
					= new ObjectInputStream(new FileInputStream(filePath));
				// 파일 읽어서 바로 setAttribute해주기
				event.getServletContext().setAttribute("list", ois.readObject());
				ois.close();
			} catch (IOException | ClassNotFoundException e) {
				e.printStackTrace();
			}
		} else {
			event.getServletContext().setAttribute("list", new ArrayList<MemberVO>());
		}

	}

}

// WAS를 종료 후 다시 켜도 그 전 정보가 남아있다.

 

VO class

MemberVO.java

package model;

import java.io.Serializable;

public class MemberVO implements Serializable {

	private static final long serialVersionUID = 1L;
	private String name;
	private String address;
	
	public MemberVO(String name, String address) {
		super();
		this.name = name;
		this.address = address;
	}

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public String getAddress() {
		return address;
	}

	public void setAddress(String address) {
		this.address = address;
	}

}

 

728x90
반응형