Skip to content

Commit e25e1e4

Browse files
Merge pull request #113 from Suzune705/suzune
feat(admin): logout user
2 parents 3682200 + 8ef5efc commit e25e1e4

9 files changed

Lines changed: 290 additions & 15 deletions

File tree

Lines changed: 66 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,66 @@
1+
/*
2+
* Click nbfs://nbhost/SystemFileSystem/Templates/Licenses/license-default.txt to change this license
3+
* Click nbfs://nbhost/SystemFileSystem/Templates/JSP_Servlet/Servlet.java to edit this template
4+
*/
5+
package com.library.controller.admin.user;
6+
7+
import com.library.dao.DaoFactory;
8+
import com.library.dao.UserDao;
9+
import com.library.dao.UserDaoImpl;
10+
import com.library.service.TrackingUserService;
11+
import com.library.service.UserService;
12+
import com.library.util.SessionTracker;
13+
import java.io.IOException;
14+
import java.io.PrintWriter;
15+
import jakarta.servlet.ServletException;
16+
import jakarta.servlet.annotation.WebServlet;
17+
import jakarta.servlet.http.HttpServlet;
18+
import jakarta.servlet.http.HttpServletRequest;
19+
import jakarta.servlet.http.HttpServletResponse;
20+
import jakarta.servlet.http.HttpSession;
21+
import org.apache.catalina.Session;
22+
import org.slf4j.Logger;
23+
import org.slf4j.LoggerFactory;
24+
25+
/**
26+
*
27+
* @author hieuchu
28+
*/
29+
@WebServlet(name = "LogoutUserController", urlPatterns = {"/admin/user/logout"})
30+
public class LogoutUserController extends HttpServlet {
31+
32+
UserDao userDao = new UserDaoImpl();
33+
private final TrackingUserService trackService = new TrackingUserService(
34+
DaoFactory.getUserSessionDao()
35+
);
36+
private final UserService userService = new UserService(
37+
DaoFactory.getUserDao(),
38+
DaoFactory.getAdminDao()
39+
);
40+
private static final Logger logger = LoggerFactory.getLogger(LogoutUserController.class);
41+
42+
@Override
43+
protected void doGet(HttpServletRequest request, HttpServletResponse response)
44+
throws ServletException, IOException {
45+
46+
String userAccount = request.getParameter("account");
47+
int userID = userDao.findUserID(userAccount);
48+
String sessionIDFromDB = trackService.getSessionID(userID);
49+
50+
HttpSession saveSessionID = SessionTracker.getSession(sessionIDFromDB);
51+
if (saveSessionID != null) {
52+
saveSessionID.invalidate();
53+
userService.setOfflineUser(userAccount);
54+
logger.info("logging out user has : {}", saveSessionID);
55+
response.sendRedirect(request.getContextPath() + "/admin/user-manager");
56+
}
57+
58+
}
59+
60+
@Override
61+
protected void doPost(HttpServletRequest request, HttpServletResponse response)
62+
throws ServletException, IOException {
63+
64+
}
65+
66+
}

src/java/com/library/controller/user/LogInController.java

Lines changed: 18 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@
1919

2020
import com.library.service.TrackingUserService;
2121
import com.library.service.UserService;
22+
import com.library.util.SessionTracker;
2223
import jakarta.servlet.http.HttpSession;
2324

2425
/**
@@ -42,6 +43,11 @@ public class LoginController extends HttpServlet {
4243
DaoFactory.getAdminDao()
4344
);
4445

46+
private final TrackingUserService trackService = new TrackingUserService(
47+
DaoFactory.getUserSessionDao()
48+
49+
);
50+
4551
@Override
4652
protected void doGet(HttpServletRequest request, HttpServletResponse response)
4753
throws ServletException, IOException {
@@ -64,19 +70,22 @@ protected void doGet(HttpServletRequest request, HttpServletResponse response)
6470
protected void doPost(HttpServletRequest request, HttpServletResponse response)
6571
throws ServletException, IOException {
6672
HttpSession session = request.getSession();
67-
String username = request.getParameter("account");
73+
String account = request.getParameter("account");
6874
String pass = request.getParameter("password");
6975

7076

71-
if (userDao.checkLogin(username, pass)) {
72-
session.setAttribute("account", username);
73-
TrackingUserService.add(username);
74-
activityService.ActivityUser(1, username);
75-
userService.setOnlineUser(username);
77+
if (userDao.checkLogin(account, pass)) {
78+
session.setAttribute("account", account);
79+
TrackingUserService.add(account);
80+
activityService.ActivityUser(1, account);
81+
userService.setOnlineUser(account);
82+
int userID = userDao.findUserID(account);
83+
trackService.updateData(session.getId(), userID);
84+
SessionTracker.addSession(session.getId(), session);
7685
response.sendRedirect(request.getContextPath() + "/book/list");
7786
} else {
7887
session.setAttribute("error", "Tên đăng nhập không tồn tại!");
79-
if (username.trim().isEmpty()) {
88+
if (account.trim().isEmpty()) {
8089
session.setAttribute("error", "Vui lòng nhập tên đăng nhập!");
8190
response.sendRedirect(request.getContextPath() + "/user/login");
8291
return;
@@ -86,8 +95,8 @@ protected void doPost(HttpServletRequest request, HttpServletResponse response)
8695
return;
8796
}
8897
// check login after user enter correcly
89-
if (userDao.checkLogin(username, pass)) {
90-
session.setAttribute("account", username);
98+
if (userDao.checkLogin(account, pass)) {
99+
session.setAttribute("account", account);
91100
response.sendRedirect(request.getContextPath() + "/book/list");
92101
return;
93102
} else {

src/java/com/library/dao/DaoFactory.java

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -43,4 +43,8 @@ public static AdminDao getAdminDao(){
4343
public static FavoriteDao getFavoriteDao(){
4444
return new FavoriteDaoImpl();
4545
}
46+
47+
public static UserSessionDao getUserSessionDao(){
48+
return new UserSessionDaoImpl();
49+
}
4650
}
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
/*
2+
* Click nbfs://nbhost/SystemFileSystem/Templates/Licenses/license-default.txt to change this license
3+
* Click nbfs://nbhost/SystemFileSystem/Templates/Classes/Class.java to edit this template
4+
*/
5+
package com.library.dao;
6+
7+
/**
8+
*
9+
* @author hieuchu
10+
*/
11+
public interface UserSessionDao {
12+
boolean canInsert(int userID);
13+
void insertData(String sessionID , int userID);
14+
void updateData(String sessionID , int userID);
15+
String getSessionID(int userID);
16+
}
Lines changed: 76 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,76 @@
1+
/*
2+
* Click nbfs://nbhost/SystemFileSystem/Templates/Licenses/license-default.txt to change this license
3+
* Click nbfs://nbhost/SystemFileSystem/Templates/Classes/Class.java to edit this template
4+
*/
5+
package com.library.dao;
6+
7+
import com.library.util.DBConnection;
8+
import java.sql.Connection;
9+
import java.sql.PreparedStatement;
10+
import java.sql.ResultSet;
11+
import java.sql.SQLException;
12+
13+
/**
14+
*
15+
* @author hieuchu
16+
*/
17+
public class UserSessionDaoImpl implements UserSessionDao {
18+
19+
@Override
20+
public void insertData(String sessionID, int userID) {
21+
String sql = "insert into user_sessions(session_id, user_id) values(? , ? )";
22+
try (
23+
Connection conn = DBConnection.getInstance().getConnection(); PreparedStatement ps = conn.prepareStatement(sql)) {
24+
ps.setString(1, sessionID);
25+
ps.setInt(2, userID);
26+
ps.executeUpdate();
27+
} catch (SQLException s) {
28+
s.printStackTrace();
29+
}
30+
}
31+
32+
@Override
33+
public String getSessionID(int userID) {
34+
String sql = "SELECT session_id FROM user_sessions WHERE user_id = ? ";
35+
try (
36+
Connection conn = DBConnection.getInstance().getConnection(); PreparedStatement ps = conn.prepareStatement(sql)) {
37+
ps.setInt(1, userID);
38+
ResultSet rs = ps.executeQuery();
39+
if (rs.next()) {
40+
return rs.getString("session_id");
41+
}
42+
} catch (SQLException s) {
43+
s.printStackTrace();
44+
}
45+
return null;
46+
}
47+
48+
@Override
49+
public boolean canInsert(int userID) {
50+
String sql = "select * from user_sessions where user_id = ? ";
51+
try (
52+
Connection conn = DBConnection.getInstance().getConnection(); PreparedStatement ps = conn.prepareStatement(sql)) {
53+
ps.setInt(1, userID);
54+
ResultSet rs = ps.executeQuery();
55+
if (rs.next()) {
56+
return false;
57+
}
58+
} catch (SQLException s) {
59+
s.printStackTrace();
60+
}
61+
return true;
62+
}
63+
64+
@Override
65+
public void updateData(String sessionID, int userID) {
66+
String sql = "update user_sessions set session_id = ? where user_id = ? ";
67+
try (
68+
Connection conn = DBConnection.getInstance().getConnection(); PreparedStatement ps = conn.prepareStatement(sql)) {
69+
ps.setString(1, sessionID);
70+
ps.setInt(2, userID);
71+
ps.executeUpdate();
72+
} catch (SQLException s) {
73+
s.printStackTrace();
74+
}
75+
}
76+
}
Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
/*
2+
* Click nbfs://nbhost/SystemFileSystem/Templates/Licenses/license-default.txt to change this license
3+
* Click nbfs://nbhost/SystemFileSystem/Templates/Classes/Class.java to edit this template
4+
*/
5+
package com.library.model.entity;
6+
7+
/**
8+
*
9+
* @author hieuchu
10+
*/
11+
public class UserSession {
12+
private String sessionID ;
13+
private User user ;
14+
15+
public UserSession() {
16+
}
17+
18+
public UserSession(String sessionID, User user) {
19+
this.sessionID = sessionID;
20+
this.user = user;
21+
}
22+
23+
public String getSessionID() {
24+
return sessionID;
25+
}
26+
27+
public void setSessionID(String sessionID) {
28+
this.sessionID = sessionID;
29+
}
30+
31+
public User getUser() {
32+
return user;
33+
}
34+
35+
public void setUser(User user) {
36+
this.user = user;
37+
}
38+
39+
}

src/java/com/library/service/TrackingUserService.java

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
*/
55
package com.library.service;
66

7+
import com.library.dao.UserSessionDao;
78
import java.util.ArrayList;
89
import java.util.List;
910

@@ -15,6 +16,12 @@
1516
*/
1617
public class TrackingUserService {
1718

19+
private final UserSessionDao userSessionDao ;
20+
21+
public TrackingUserService(UserSessionDao userSessionDao){
22+
this.userSessionDao = userSessionDao;
23+
24+
}
1825
private static final List<String> list = new ArrayList<>();
1926

2027
public static void add(String account){
@@ -27,5 +34,20 @@ public static int getSize(){
2734
return list.size();
2835
}
2936

37+
/**
38+
* updateDate : insert data into user_session table after user login in
39+
*/
40+
41+
public void updateData(String sessionID, int userID){
42+
if(this.userSessionDao.canInsert(userID)){
43+
this.userSessionDao.insertData(sessionID, userID);
44+
}else{
45+
this.userSessionDao.updateData(sessionID, userID);
46+
}
47+
}
48+
49+
public String getSessionID(int userID){
50+
return this.userSessionDao.getSessionID(userID);
51+
}
3052

3153
}
Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
/*
2+
* Click nbfs://nbhost/SystemFileSystem/Templates/Licenses/license-default.txt to change this license
3+
* Click nbfs://nbhost/SystemFileSystem/Templates/Classes/Class.java to edit this template
4+
*/
5+
package com.library.util;
6+
7+
import jakarta.servlet.http.HttpSession;
8+
import jakarta.servlet.http.HttpSessionEvent;
9+
import jakarta.servlet.http.HttpSessionListener;
10+
import java.util.Collection;
11+
import java.util.HashMap;
12+
import java.util.Map;
13+
14+
/**
15+
*
16+
* @author hieuchu
17+
*/
18+
public class SessionTracker implements HttpSessionListener {
19+
20+
private static final Map<String, HttpSession> map = new HashMap<>();
21+
22+
@Override
23+
public void sessionCreated(HttpSessionEvent se) {
24+
map.put(se.getSession().getId(), se.getSession());
25+
}
26+
27+
@Override
28+
public void sessionDestroyed(HttpSessionEvent se) {
29+
map.remove(se.getSession().getId());
30+
}
31+
32+
public static HttpSession getSession(String sessionID){
33+
return map.get(sessionID);
34+
}
35+
36+
public static void addSession(String sessionID, HttpSession se){
37+
map.put(sessionID, se);
38+
}
39+
40+
public static Collection<HttpSession> getAll(){
41+
return map.values();
42+
}
43+
}

web/WEB-INF/views/admin/usermanager.jsp

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -750,10 +750,10 @@
750750

751751
<td>
752752
<div class="actions">
753-
<button class="btn btn-warning btn-sm" onclick="logoutUser(${user.userID})">
753+
<button class="btn btn-warning btn-sm" onclick="logoutUser('${user.account}')">
754754
<i class="fa-solid fa-right-from-bracket"></i> Logout
755755
</button>
756-
<button class="btn btn-danger btn-sm" onclick="deleteUser(${user.userID})">
756+
<button class="btn btn-danger btn-sm" onclick="deleteUser('${user.account}')">
757757
<i class="fa-solid fa-trash"></i> Delete
758758
</button>
759759
</div>
@@ -814,15 +814,15 @@
814814
<p>&copy; 2025 Library Management System. All rights reserved.</p>
815815
</footer>
816816
<script>
817-
function logoutUser(userID) {
817+
function logoutUser(account) {
818818
if (confirm('Are you sure you want to log out this user?')) {
819-
window.location.href = '${pageContext.request.contextPath}/admin/users/logout?id=' + userID;
819+
window.location.href = '${pageContext.request.contextPath}/admin/user/logout?account=' + account;
820820
}
821821
}
822822
823-
function deleteUser(userID) {
823+
function deleteUser(account) {
824824
if (confirm('Are you sure you want to delete this user?')) {
825-
window.location.href = '${pageContext.request.contextPath}/admin/users/delete?id=' + userID;
825+
window.location.href = '${pageContext.request.contextPath}/admin/user/delete?account=' + account;
826826
}
827827
}
828828

0 commit comments

Comments
 (0)