제목 | Java Spring 세션 남은 시간 표시 | ||||||
글쓴이 | 이지섭 | 작성일 | 2025-06-29 | 수정일 | 2025-07-02 | 조회수 | 38 |
Java, Spring 에서 로그인 세션의 남은 시간을 보여주는 것이다.
Spring Boot 에서는 좀 다른 방식으로 구현할 수 있지만, Spring framework 에서 구현하는 방식을 설명한다. web.xml 파일을 이용한다.
*.do 또는 /api/* 백앤드 호출에서 필터를 적용하여, 로그인 세션의 종료될 시간을 쿠키에 세팅하고, 프론트 단에서 쿠키 값을 읽어서 남은 시간을 표시한다.
SessionTimeoutCookieFilter 필터 클래스에서 @Component("sessionTimeoutCookieFilterBean") 으로 선언한다.
Spring에서 Filter에 DI 를 적용하려면 DelegatingFilterProxy 를 사용해야 한다. DI 는 세션의 유지 시간을 구해오는 서비스를 Autowired 하기 위함이다.
본 소스에서는 personalInfoService.selectSystemEnv(); 으로 세션 유지 시간을 구해온다.
package isry.itgcms.sysmgmt.util; import java.io.IOException; import java.util.Map; import javax.servlet.Filter; import javax.servlet.FilterChain; import javax.servlet.FilterConfig; import javax.servlet.ServletException; import javax.servlet.ServletRequest; import javax.servlet.ServletResponse; import javax.servlet.http.Cookie; //import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Component; import isry.itgcms.sysmgmt.personalinfo.service.PersonalInfoService; @Component("sessionTimeoutCookieFilterBean") public class SessionTimeoutCookieFilter implements Filter { @SuppressWarnings("unused") private FilterConfig config; @Autowired private PersonalInfoService personalInfoService; public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException { HttpServletResponse httpResponse = (HttpServletResponse) response; //HttpServletRequest httpRequest = (HttpServletRequest) request; int sessionTime = 30; try { Map map = personalInfoService.selectSystemEnv(); sessionTime = Integer.parseInt(map.get("SESIN_TMOUT_HR")); } catch (Exception e) { e.printStackTrace(); } long sessionDurationTime = System.currentTimeMillis() + sessionTime * 60 * 1000; Cookie cookie = new Cookie("sessionDurationTime", "" + sessionDurationTime); //cookie.setSecure(true); cookie.setPath("/"); httpResponse.addCookie(cookie); chain.doFilter(request, response); } public void init(FilterConfig config) throws ServletException { this.config = config; } public void destroy() { } }
아래는 web.xml 파일에서 필터를 등록하는 부분이다. 필터 클래스를 org.springframework.web.filter.DelegatingFilterProxy 으로 하고, @Component("sessionTimeoutCookieFilterBean") 으로 선언했던 필터 Bean 을 등록한다.
url-pattern 에는 *.do 또는 /api/* 등의 패턴을 적용한다. 선택적인 사항이다. 백앤드 프로그램이 호출될 때마다 세션 유지 시간이 재 설정되는 것이다.
<filter> <filter-name>sessionTimeoutCookieFilterBean</filter-name> <filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class> <async-supported>true</async-supported> <!-- Support Async --> </filter> <filter-mapping> <filter-name>sessionTimeoutCookieFilterBean</filter-name> <url-pattern>*.do</url-pattern> <!-- Your Choice 1 --> <url-pattern>/api/*</url-pattern> <!-- Your Choice 2 --> </filter-mapping>
아래는 프론트 단의 소스이다. 쿠키에서 세션이 종료될 시간을 읽어와서 남은 시간을 표시해준다.
<html> <head> <title>Time Left</title> <script type="text/javascript"> var timeInterval = 1000; // 1-second interval calls var timer; var timerArr = new Array(); function init() { showRemaining(); timer = setInterval(showRemaining, timeInterval); // 1-second interval calls timerArr.push(timer); } function showRemaining() { var timeRemaining = Number(getCookie("sessionDurationTime")) - new Date().getTime(); //console.log("sessionDurationTime", getCookie("sessionDurationTime")); //console.log("unix time", new Date().getTime()); //console.log("timeRemaining", timeRemaining); if (timeRemaining < timeInterval) { for (var i = 0; i < timerArr.length; i++) { clearInterval(timerArr[i]); } timerArr = new Array(); setTimeout(function() { alert("Session expired."); }, 1000); return; } var timeHour = Math.floor(timeRemaining / 1000 / 60 / 60); var timeMin = Math.floor((timeRemaining / 1000 / 60) % 60); var timeSec = Math.floor((timeRemaining / 1000) % 60); const formattedHours = String(timeHour).padStart(2, '0'); const formattedMinutes = String(timeMin).padStart(2, '0'); const formattedSeconds = String(timeSec).padStart(2, '0'); document.getElementById("timeRemaining").innerHTML = formattedHours + ":" + formattedMinutes + ":" + formattedSeconds; } function getCookie(psName) { var vsCookie = document.cookie + ";"; var vaItems = vsCookie.split(";"); var vnItemLen = vaItems.length; var item = null; var voItemInfo = null; for (var i = 0; i < vnItemLen; i++) { item = vaItems[i]; voItemInfo = item.split("="); if (psName == voItemInfo[0].trim()) { return unescape(voItemInfo[1]); } } return ""; } </script> </head> <body onload="init();"> Time remaining : <span id="timeRemaining"></span> </body> </html>
스프링 부트에서는 아래와 같이 필터를 등록할 수 있다.
import org.springframework.boot.web.servlet.FilterRegistrationBean; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import isry.itgcms.sysmgmt.util.SessionTimeoutCookieFilter; @Configuration public class MyFilterConfig { @Bean public FilterRegistrationBean sessionTimeoutCookieFilter() { FilterRegistrationBean registration = new FilterRegistrationBean<>(); registration.setFilter(new SessionTimeoutCookieFilter()); registration.addUrlPatterns("*.do"); registration.addUrlPatterns("/api/*"); registration.setAsyncSupported(true); return registration; } }
Async Supported 는 필수 사항은 아니지만, 경우에 따라서는 필요할 수도 있습니다.
[ 참조한 페이지 ]
| |||||||
첨부파일 | SessionTimeoutCookieFilter.java (1,927 byte) timeLeft.html (2,095 byte) | ||||||
로그인 | Language : |