How to invalidate an user session when he logs twice with the same credentials

后端 未结 3 1855
粉色の甜心
粉色の甜心 2020-11-27 17:00

I\'m using JSF 1.2 with Richfaces and Facelets.

I have an application with many session-scoped beans and some application beans.

The user logs in with, let\'

3条回答
  •  自闭症患者
    2020-11-27 17:52

    The DB-independent approach would be to let the User have a static Map variable and implement HttpSessionBindingListener (and Object#equals() and Object#hashCode()). This way your webapp will still function after an unforeseen crash which may cause that the DB values don't get updated (you can of course create a ServletContextListener which resets the DB on webapp startup, but that's only more and more work).

    Here's how the User should look like:

    public class User implements HttpSessionBindingListener {
    
        // All logins.
        private static Map logins = new ConcurrentHashMap<>();
    
        // Normal properties.
        private Long id;
        private String username;
        // Etc.. Of course with public getters+setters.
    
        @Override
        public boolean equals(Object other) {
            return (other instanceof User) && (id != null) ? id.equals(((User) other).id) : (other == this);
        }
    
        @Override
        public int hashCode() {
            return (id != null) ? (this.getClass().hashCode() + id.hashCode()) : super.hashCode();
        }
    
        @Override
        public void valueBound(HttpSessionBindingEvent event) {
            HttpSession session = logins.remove(this);
            if (session != null) {
                session.invalidate();
            }
            logins.put(this, event.getSession());
        }
    
        @Override
        public void valueUnbound(HttpSessionBindingEvent event) {
            logins.remove(this);
        }
    
    }
    

    When you login the User as follows:

    User user = userDAO.find(username, password);
    if (user != null) {
        sessionMap.put("user", user);
    } else {
        // Show error.
    }
    

    then it will invoke the valueBound() which will remove any previously logged in user from the logins map and invalidate the session.

    When you logout the User as follows:

    sessionMap.remove("user");
    

    or when the session is timed out, then the valueUnbound() will be invoked which removes the user from the logins map.

提交回复
热议问题