Java8
전자정부프레임워크 3.9
10.4.27-MariaDB
MyBatis
CentOS Linux release 7.9.2009 (Core)
JSP/Servlet 환경에서는 접속한 클라이언트에 대한 정보는
HttpSession
객체에 담아 표현한다.HttpSession
객체는 HTTP 요청 시 생성되었다가 응답 시 사라지는ServletRequest
객체와는 다르게 JSP나 Servlet에 의해 생성된 후 설정된timeout
에 따라서 제거된다.
HttpSession
객체가 생성되고 제거될 때 발생되는 이벤트가 HttpSessionEvent이며, 이 이벤트를 처리하는 리스너가HttpSessionListener
이다.
리스너는 위와 같이 interface 형태로 API가 제공되므로 이 리스너를 구현하여 설정으로 등록해주면 된다. 서블릿 컨테이너는
HttpSessionEvent
가 발생한 시점에 자신에게 등록된HttpSessionListener
구현체가 있는지 확인하고, 등록된 리스너가 있으면 세션이 생성된 시점에 해당 리스너의sessionCreated()
를 세션이 제거되는 시점에sessionDestroyed()
를 호출한다.
// VisitCountService
public interface VisitCountService {
void insertVisitCount();
void updateVisitCount();
VisitCountVO selectVisitCount();
}
// VisitCountDAO
@Repository("visitCountDAO")
public class VisitCountDAO extends EgovComAbstractDAO {
public void insertVisitCount() {
insert("visitCountMapper.insertVisitCount");
}
public void updateVisitCount() {
update("visitCountMapper.updateVisitCount");
}
public VisitCountVO selectVisitCount() {
return selectOne("visitCountMapper.selectVisitCount");
}
}
// VisitCountServiceImpl
@Service("visitCountService")
public class VisitCountServiceImpl extends EgovAbstractServiceImpl implements VisitCountService {
@Resource(name = "visitCountDAO")
private VisitCountDAO visitCountDAO;
@Override
public void insertVisitCount() {
visitCountDAO.insertVisitCount();
}
@Override
public void updateVisitCount() {
visitCountDAO.updateVisitCount();
}
@Override
public VisitCountVO selectVisitCount() {
return visitCountDAO.selectVisitCount();
}
}
// VisitCountVO
public class VisitCountVO {
private String regDate;
private int visitCount;
public String getRegDate() {
return regDate;
}
public int getVisitCount() {
return visitCount;
}
public void setRegDate(String regDate) {
this.regDate = regDate;
}
public void setVisitCount(int visitCount) {
this.visitCount = visitCount;
}
@Override
public String toString() {
return "VisitCountVO{" +
"regDate='" + regDate + '\'' +
", visitCount=" + visitCount +
'}';
}
}
// VisitCount_SQL_maria.xml
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="visitCountMapper">
<insert id="insertVisitCount">
INSERT INTO SPW_VISIT_COUNT
(REG_DATE, VISIT_COUNT)
VALUES
(NOW(), 1);
</insert>
<update id="updateVisitCount">
UPDATE
SPW_VISIT_COUNT
SET
VISIT_COUNT = SPW_VISIT_COUNT.VISIT_COUNT + 1
WHERE
REG_DATE = DATE_FORMAT(NOW(), '%Y-%m-%d')
</update>
<select id="selectVisitCount" resultType="VisitCountVO">
SELECT
REG_DATE, VISIT_COUNT
FROM
SPW_VISIT_COUNT
where
REG_DATE = DATE_FORMAT(NOW(), '%Y-%m-%d')
</select>
</mapper>
DB에 접속 정보를 저장하기 위한 서비스 및 VO이다.
public class HttpSessionListener implements javax.servlet.http.HttpSessionListener {
private static int todayVisitCount;
public static int getTodayVisitCount() {
return todayVisitCount;
}
public static void setTodayVisitCount(int count) {
todayVisitCount = count;
}
@Override
public void sessionCreated(HttpSessionEvent se) {
HttpSession session = se.getSession();
WebApplicationContext ctx = WebApplicationContextUtils.getWebApplicationContext(session.getServletContext());
VisitCountService visitCountService = ctx.getBean("visitCountService", VisitCountService.class);
if(session.isNew()){
VisitCountVO visitCountVO = visitCountService.selectVisitCount();
if(visitCountVO == null) {
visitCountService.insertVisitCount();
setTodayVisitCount(1);
} else {
visitCountService.updateVisitCount();
setTodayVisitCount(visitCountVO.getVisitCount() + 1);
}
}
}
@Override
public void sessionDestroyed(HttpSessionEvent se) {
}
}
세션이 생성되는 시점에, 금일 날짜에 해당하는 접속 기록이 있으면
VisitCount
를 1 증가시키고, 없으면VisitCount
를 등록하는 로직이다.
// web.xml
<listener>
<listener-class>breeze.marketing.service.HttpSessionListener</listener-class>
</listener>
web.xml에 위와 같이 listener를 등록해주면 사용 가능하다.
@WebListener
public class HttpSessionListener implements javax.servlet.http.HttpSessionListener {
...
Servlet 3.0 버전 이상이면 위와 같이
@WebListener
어노테이션을 붙여주는 방법도 있다.
...
<p class="today">TODAY : <span class="num"><%= HttpSessionListener.getTodayVisitCount()%></span>명</p>
...
static 메소드를 불러와 사용이 가능하다.