You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@tomcat.apache.org by Gokul Singh <go...@wipro.com> on 2001/01/15 06:04:31 UTC

Re: NullPointerException from HttpSessionFacade.invalidate()

Hans Bergsten wrote:
> [...]

> The spec may not be explicit enough about this, but the session object
> you get back from the getSession() object is a container-managed object
> that the application is not supposed/allowed to keep long-lived
> references 
> to. It's the same as with all other container-objects made available to
> the
> application; request, response, JSP tag handlers, etc.

> I'm not sure why you're keeping references to the session objects in
> you're application, but if you describe what you're trying to do I'm
> sure I can give you a hint about another way to accomplish the same
> thing without the problems you have with your current solution.

 I am trying to disallow a single user to have multiple login sessions valid at any given time. I have to enforce this even if the user tried to login from two different machines.
Can you suggest a solution for this which works on tomcat 3.2.1 and uses servlet specs 2.2 only.

Regds,
Gokul


Re: NullPointerException from HttpSessionFacade.invalidate()

Posted by "Craig R. McClanahan" <Cr...@eng.sun.com>.
Gokul Singh wrote:

> Hans Bergsten wrote:
> > [...]
>
> > The spec may not be explicit enough about this, but the session object
> > you get back from the getSession() object is a container-managed object
> > that the application is not supposed/allowed to keep long-lived
> > references
> > to. It's the same as with all other container-objects made available to
> > the
> > application; request, response, JSP tag handlers, etc.> I'm not sure why
> you're keeping references to the session objects in
> > you're application, but if you describe what you're trying to do I'm
> > sure I can give you a hint about another way to accomplish the same
> > thing without the problems you have with your current solution.  I am trying
> to disallow a single user to have multiple login sessions valid at any given
> time. I have to enforce this even if the user tried to login from two
> different machines.Can you suggest a solution for this which works on tomcat
> 3.2.1 and uses servlet specs 2.2 only.
>  Regds,Gokul

When I had to do something similar, I maintained a Hashtable in a servlet
context attribute that was keyed by username rather than by session id.  My
login logic (that processed the username and password) checked for the username
already being in this Hashtable, and disallowed a login if it was already
there.  For logout, I also stuck in a session attribute which implemented
HttpSessionBindingListener, so that I could remove this user's entry when the
current session was invalidated.

As others will undoubtedly point out, you still get to face the usual set of
issues when a user has multiple windows open on the same client machine.

Craig


Re: NullPointerException from HttpSessionFacade.invalidate()

Posted by Hans Bergsten <ha...@gefionsoftware.com>.
Gokul Singh wrote:
> 
> ----- Original Message -----
> From: "Hans Bergsten" <ha...@gefionsoftware.com>
> 
> > > Gokul Singh wrote:
> > >
> > > Hans Bergsten wrote:
> > > > [...]
> > >
> > >  I am trying to disallow a single user to have multiple login sessions
> > > valid at any given time. I have to enforce this even if the user tried
> > > to login from two different machines.
> 
> A small addition here. The requirement is that the user be allowed to login
> by creating a new session on login request and invalidating any valid
> session that he may have at that time.
> To be more elaborate.
> 1. A user U logs in and has a session associated with him i.e. S1.
> 2. user U goes to another machine and tries to login.
> 3. The user U should get a new session S2 with S1 being invalidated.
> 
> I hope the requirements are now clear.

Okay, that's very different ;-)

> [...]
> The requirement is that the user can login any no. of times he wants. But he
> should have only one valid session and that should be the session from the
> last successful login attempt as mentioned above.
> 
> Can you please tell me if this is possible using 2.2 specs and tomcat 3.2.1

Probably not by basing it on the standard session mechanism, since
requests within one session can not access or invalidate another
session. Again, this would not be possible even if the same
HttpSession instance was kept throughout the session.

But I must admit that I find the requirement a bit strange, since to me
it
amounts to pretty much the same as allowing multiple concurrent logins 
from the same user. Why does it matter if a user has more than one
session 
active at the same time, on two different machines? What is it you want 
to accomplish by only allowing one valid session at a time? Anyway, you 
may have to look at a combination of a currentUsers list as a context 
attribute and your own "session data store", also as a context
attribute, 
or in a database or some other external storage facility.

> PS: I have joined this list today only. I am not sure if this posting is
> appropriate for this list or not.
> If it is inappropriate here, then please mail to me privately.

By now, this is off-topic for this list. So if you want to continue
the discussion, I suggest you mail me privately.

Hans
-- 
Hans Bergsten		hans@gefionsoftware.com
Gefion Software		http://www.gefionsoftware.com
Author of JavaServer Pages (O'Reilly), http://TheJSPBook.com

Re: NullPointerException from HttpSessionFacade.invalidate()

Posted by Gokul Singh <go...@wipro.com>.
----- Original Message -----
From: "Hans Bergsten" <ha...@gefionsoftware.com>


> > Gokul Singh wrote:
> >
> > Hans Bergsten wrote:
> > > [...]
> >
> >  I am trying to disallow a single user to have multiple login sessions
> > valid at any given time. I have to enforce this even if the user tried
> > to login from two different machines.

A small addition here. The requirement is that the user be allowed to login
by creating a new session on login request and invalidating any valid
session that he may have at that time.
To be more elaborate.
1. A user U logs in and has a session associated with him i.e. S1.
2. user U goes to another machine and tries to login.
3. The user U should get a new session S2 with S1 being invalidated.

I hope the requirements are now clear.


> archives for details). The bottom line is that a session is associated
> with a "client", not a "user".

Agreed.

> > Can you suggest a solution for this which works on tomcat 3.2.1 and
> > uses servlet specs 2.2 only.
>
> Something like this should work in any compliant container.

Thanks for putting down the whole code for me. I already implement this
philosophy in my code. But the requirements are slightly different as
spelled above.


> To make sure a user only logs in once, check if the loginID is
> already in the context structure before allowing a new login
> and creating the UserBean.

The requirement is that the user can login any no. of times he wants. But he
should have only one valid session and that should be the session from the
last successful login attempt as mentioned above.

Can you please tell me if this is possible using 2.2 specs and tomcat 3.2.1


Regds,
Gokul

PS: I have joined this list today only. I am not sure if this posting is
appropriate for this list or not.
If it is inappropriate here, then please mail to me privately.


>
> Hans
> --



Re: NullPointerException from HttpSessionFacade.invalidate()

Posted by Hans Bergsten <ha...@gefionsoftware.com>.
> Gokul Singh wrote:
> 
> Hans Bergsten wrote:
> > [...]
> 
> > The spec may not be explicit enough about this, but the session
> object
> > you get back from the getSession() object is a container-managed
> object
> > that the application is not supposed/allowed to keep long-lived
> > references
> > to. It's the same as with all other container-objects made available
> to
> > the
> > application; request, response, JSP tag handlers, etc.
> > I'm not sure why you're keeping references to the session objects in
> > you're application, but if you describe what you're trying to do I'm
> > sure I can give you a hint about another way to accomplish the same
> > thing without the problems you have with your current solution.
> 
>  I am trying to disallow a single user to have multiple login sessions
> valid at any given time. I have to enforce this even if the user tried
> to login from two different machines.

Okay, in that case comparing HttpSession objects wouldn't work even
if Tomcat kept the same instance throughout the session. If the user
tries to log in from two different machines, he/she would get always
get two different sessions. Even when using two different browser
windows on the same machine, he/she may end up with two different
sessions (long story, search the JSP- and SERVLET-INTEREST list
archives for details). The bottom line is that a session is associated
with a "client", not a "user".

> Can you suggest a solution for this which works on tomcat 3.2.1 and
> uses servlet specs 2.2 only.

Something like this should work in any compliant container.

Create an instance of a class that implements the
javax.servlet.http.HttpSessionBindingListener interface and save it
in the session when the user logs in. Give the instance references
to the ServletContext and the user's login ID. In the valueBound() 
method, add the loginID to a data structure kept as a context attribute, 
and in the valueUnbound() method, remove the user info from the data 
structure:

  public class UserBean implements HttpSessionBindingListener,
    Serializable {

    private ServletContext context;
    private String loginID;

    public UserBean(ServletContext context, String loginID) {
      this.context = context;
      this.loginID = loginID;
    }

    public void valueBound(HttpSessionBindingEvent e) {
      Vector currentUsers = 
        (Vector) context.getAttribute("currentUsers");
      if (currentUsers == null) {
        currentUsers = new Vector();
      }
      currentUsers.addElement(loginID);
    }

    public void valueUnbound(HttpSessionBindingEvent e) {
      Vector currentUsers = 
        (Vector) context.getAttribute("currentUsers");
      currentUsers.removeElement(loginID);
      
    }
  }

To make sure a user only logs in once, check if the loginID is
already in the context structure before allowing a new login
and creating the UserBean.

Hans
-- 
Hans Bergsten		hans@gefionsoftware.com
Gefion Software		http://www.gefionsoftware.com
Author of JavaServer Pages (O'Reilly), http://TheJSPBook.com