costin      00/11/21 16:10:00

  Modified:    src/share/org/apache/tomcat/modules/session SessionId.java
                        SimpleSessionStore.java
               src/share/org/apache/tomcat/session ServerSession.java
                        ServerSessionManager.java
               src/share/org/apache/tomcat/util/threads TimeStamp.java
  Log:
  Merged fixes from 3.2 - thanks pfrieden, hans, shai, craig.
  
  - fix for "load balancing"
  - check the session id, multiple cookies ( this will be enhanced as the
  session code is cleaned up/refactored )
  - "no cookies" option
  
  Submitted by: [EMAIL PROTECTED], [EMAIL PROTECTED], [EMAIL PROTECTED]
  
  Revision  Changes    Path
  1.2       +77 -46    
jakarta-tomcat/src/share/org/apache/tomcat/modules/session/SessionId.java
  
  Index: SessionId.java
  ===================================================================
  RCS file: 
/home/cvs/jakarta-tomcat/src/share/org/apache/tomcat/modules/session/SessionId.java,v
  retrieving revision 1.1
  retrieving revision 1.2
  diff -u -r1.1 -r1.2
  --- SessionId.java    2000/11/21 00:31:12     1.1
  +++ SessionId.java    2000/11/22 00:09:59     1.2
  @@ -62,6 +62,8 @@
   import org.apache.tomcat.core.*;
   import org.apache.tomcat.util.*;
   import org.apache.tomcat.helper.*;
  +import org.apache.tomcat.session.ServerSessionManager;
  +import org.apache.tomcat.session.ServerSession;
   import java.io.*;
   import java.net.*;
   import java.util.*;
  @@ -80,15 +82,20 @@
    *
    * This implementation only handles Cookies and URL rewriting sessions,
    * please extend or add new interceptors for other methods.
  - *
  + * 
  + * You can set this interceptor to not use cookies, but only rewriting.
    *
  + * @author [EMAIL PROTECTED]
  + * @author Shai Fultheim [[EMAIL PROTECTED]]
    */
   public class SessionId extends  BaseInterceptor
   {
  -
  +    private int manager_note;
  +    
       // GS, separates the session id from the jvm route
       static final char SESSIONID_ROUTE_SEP = '.';
       ContextManager cm;
  +    boolean noCookies=false;
       
       public SessionId() {
       }
  @@ -97,6 +104,17 @@
        this.cm=cm;
       }
   
  +    public void setNoCookies(boolean noCookies) {
  +        this.noCookies = noCookies;
  +    }
  +
  +    public void engineInit( ContextManager cm ) throws TomcatException {
  +     // set-up a per/container note for StandardManager
  +     // the standard manager is used to verify the session ID.
  +     manager_note = cm.getNoteId( ContextManager.CONTAINER_NOTE,
  +                                  "tomcat.standardManager");
  +    }
  +
       /** Extract the session id from the request.
        * SessionInterceptor will have to be called _before_ mapper,
        * to avoid coding session stuff inside the mapper.
  @@ -119,8 +137,8 @@
        
        if ((foundAt=uri.indexOf(sig))!=-1){
            sessionId=uri.substring(foundAt+sig.length());
  -         // I hope the optimizer does it's job:-)
  -         sessionId = fixSessionId( request, sessionId );
  +         // FIX [EMAIL PROTECTED]: reloading 
  +         //      sessionId = fixSessionId( request, sessionId );
            
            // rewrite URL, do I need to do anything more?
            request.requestURI().setString(uri.substring(0, foundAt));
  @@ -138,9 +156,16 @@
        */
       public int requestMap(Request request ) {
        String sessionId = null;
  +     Context ctx=request.getContext();
  +     if( ctx==null ) {
  +         log( "Configuration error in StandardSessionInterceptor " +
  +              " - no context " + request );
  +         return 0;
  +     }
  +
   
        int count=request.getCookieCount();
  -     
  +
        // Give priority to cookies. I don't know if that's part
        // of the spec - XXX
        for( int i=0; i<count; i++ ) {
  @@ -148,54 +173,55 @@
            
            if (cookie.getName().equals("JSESSIONID")) {
                sessionId = cookie.getValue().toString();
  -             sessionId = fixSessionId( request, sessionId );
  -
  -             // XXX what if we have multiple session cookies ?
  -             // right now only the first is used
  -             request.setRequestedSessionId( sessionId );
  -             request.setSessionIdSource( Request.SESSIONID_FROM_COOKIE);
  -             break;
  +             if (debug > 0) log("Found session id cookie " +
  +                                sessionId);
  +             // 3.2 - load balancing fix
  +             // sessionId = fixSessionId( request, sessionId );
  +             // 3.2 - PF ( [EMAIL PROTECTED] ): check the session id from
  +             // cookies for validity
  +
  +             ServerSessionManager sM = getManager( ctx );
  +             ServerSession sess = sM.findSession(sessionId);
  +             if (sess != null) {
  +                 request.setRequestedSessionId( sessionId );
  +                 request.setSessionIdSource(Request.SESSIONID_FROM_COOKIE );
  +                 // since we verified this sessionID, we can also set
  +                 // it and adjust the session
  +                 request.setSession( sess );
  +                 request.setSessionId( sessionId );
  +                 break;
  +             }
            }
        }
   
        return 0;
       }
  -
  -//     private void findSessionCookie( MimeHeaders headers ) {
  -//   int pos=0;
  -//   while( pos>=0 ) {
  -//       pos=headers.findHeader( "Cookie", pos );
  -//       // no more cookie headers headers
  -//       if( pos<0 ) break;
   
  -//       MessageBytes cookieValue=getValue( pos );
  -         
  +//     /** Fix the session id. If the session is not valid return null.
  +//      *  It will also clean up the session from load-balancing strings.
  +//      * @return sessionId, or null if not valid
  +//      */
  +//     private String fixSessionId(Request request, String sessionId){
  +//   // GS, We piggyback the JVM id on top of the session cookie
  +//   // Separate them ...
  +
  +//   if( debug>0 ) cm.log(" Orig sessionId  " + sessionId );
  +//   if (null != sessionId) {
  +//       int idex = sessionId.lastIndexOf(SESSIONID_ROUTE_SEP);
  +//       if(idex > 0) {
  +//           sessionId = sessionId.substring(0, idex);
  +//       }
   //   }
  +//   return sessionId;
   //     }
  -    
  -    /** Fix the session id. If the session is not valid return null.
  -     *  It will also clean up the session from load-balancing strings.
  -     * @return sessionId, or null if not valid
  -     */
  -    private String fixSessionId(Request request, String sessionId){
  -     // GS, We piggyback the JVM id on top of the session cookie
  -     // Separate them ...
  -
  -     if( debug>0 ) cm.log(" Orig sessionId  " + sessionId );
  -     if (null != sessionId) {
  -         int idex = sessionId.lastIndexOf(SESSIONID_ROUTE_SEP);
  -         if(idex > 0) {
  -             sessionId = sessionId.substring(0, idex);
  -         }
  -     }
  -     return sessionId;
  -    }
   
       public int beforeBody( Request rrequest, Response response ) {
        String reqSessionId = rrequest.getSessionId();
        if( debug>0 ) cm.log("Before Body " + reqSessionId );
        if( reqSessionId==null)
            return 0;
  +        if (noCookies)
  +            return 0;
   
        
           // GS, set the path attribute to the cookie. This way
  @@ -206,13 +232,13 @@
               sessionPath = "/";
           }
   
  -        // GS, piggyback the jvm route on the session id.
  -        if(!sessionPath.equals("/")) {
  -            String jvmRoute = rrequest.getJvmRoute();
  -            if(null != jvmRoute) {
  -                reqSessionId = reqSessionId + SESSIONID_ROUTE_SEP + jvmRoute;
  -            }
  -        }
  +//         // GS, piggyback the jvm route on the session id.
  +//  //        if(!sessionPath.equals("/")) {
  +//             String jvmRoute = rrequest.getJvmRoute();
  +//             if(null != jvmRoute) {
  +//                 reqSessionId = reqSessionId + SESSIONID_ROUTE_SEP + jvmRoute;
  +//             }
  +//  //     }
   
        // we know reqSessionId doesn't need quoting ( we generate it )
        StringBuffer buf = new StringBuffer();
  @@ -234,6 +260,11 @@
                            buf.toString());
        
        return 0;
  +    }
  +
  +    // -------------------- Internal methods --------------------
  +    private ServerSessionManager getManager( Context ctx ) {
  +     return (ServerSessionManager)ctx.getContainer().getNote(manager_note);
       }
   
   
  
  
  
  1.2       +22 -3     
jakarta-tomcat/src/share/org/apache/tomcat/modules/session/SimpleSessionStore.java
  
  Index: SimpleSessionStore.java
  ===================================================================
  RCS file: 
/home/cvs/jakarta-tomcat/src/share/org/apache/tomcat/modules/session/SimpleSessionStore.java,v
  retrieving revision 1.1
  retrieving revision 1.2
  diff -u -r1.1 -r1.2
  --- SimpleSessionStore.java   2000/11/21 00:31:13     1.1
  +++ SimpleSessionStore.java   2000/11/22 00:09:59     1.2
  @@ -84,6 +84,9 @@
    * session stuff ( cookie, rewrite, etc)
    *
    * @author [EMAIL PROTECTED]
  + * @author [EMAIL PROTECTED]
  + * @author [EMAIL PROTECTED]
  + * @author Shai Fultheim [[EMAIL PROTECTED]]
    */
   public final class SimpleSessionStore  extends BaseInterceptor {
       int manager_note;
  @@ -144,10 +147,24 @@
            // context and one for the real context... or old session
            // cookie. We must check for validity in the current context.
            ServerSessionManager sM = getManager( ctx );    
  -         ServerSession sess= sM.findSession( sessionId );
  -         //      log("Try to find: " + sessionId );
  +         ServerSession sess= request.getSession( false );
  +
  +         // if not set already, try to find it using the session id
  +         if( sess==null )
  +             sess=sM.findSession( sessionId );
  +
  +         // 3.2 - Hans fix ( use the session id from URL ) - it's
  +         // part of the current code
  +
  +         // 3.2 - PF ( [EMAIL PROTECTED] ): fix moved to SessionId.
  +         // ( check if the ID is valid before setting it, do that
  +         //  for cookies since we can have multiple cookies, some
  +         //  from old sessions )
  +
            if(null != sess) {
  +             // touch it 
                sess.getTimeStamp().touch( System.currentTimeMillis() );
  +
                //log("Session found " + sessionId );
                // set it only if nobody else did !
                if( null == request.getSession( false ) ) {
  @@ -207,7 +224,9 @@
   
        if( request.getSession( false ) != null )
            return 0; // somebody already set the session
  -     ServerSession newS=sM.getNewSession();
  +
  +     // Fix from Shai Fultheim: load balancing needs jvmRoute
  +     ServerSession newS=sM.getNewSession(request.getJvmRoute());
        request.setSession( newS );
        request.setSessionId( newS.getId().toString());
        return 0;
  
  
  
  1.8       +1 -1      
jakarta-tomcat/src/share/org/apache/tomcat/session/ServerSession.java
  
  Index: ServerSession.java
  ===================================================================
  RCS file: 
/home/cvs/jakarta-tomcat/src/share/org/apache/tomcat/session/ServerSession.java,v
  retrieving revision 1.7
  retrieving revision 1.8
  diff -u -r1.7 -r1.8
  --- ServerSession.java        2000/11/21 00:31:14     1.7
  +++ ServerSession.java        2000/11/22 00:09:59     1.8
  @@ -75,7 +75,7 @@
    *  - serializable ( by external components )
    *
    * Components:
  - *  - timestamp ( expire )
  + *  - timestamp ( expire ) 
    *  - id
    *  - name/value repository
    *
  
  
  
  1.13      +5 -2      
jakarta-tomcat/src/share/org/apache/tomcat/session/ServerSessionManager.java
  
  Index: ServerSessionManager.java
  ===================================================================
  RCS file: 
/home/cvs/jakarta-tomcat/src/share/org/apache/tomcat/session/ServerSessionManager.java,v
  retrieving revision 1.12
  retrieving revision 1.13
  diff -u -r1.12 -r1.13
  --- ServerSessionManager.java 2000/11/21 00:31:14     1.12
  +++ ServerSessionManager.java 2000/11/22 00:09:59     1.13
  @@ -100,7 +100,6 @@
       long maxInactiveInterval;
       
       protected Reaper reaper;
  -
       Random randomSource=null;
       
       public ServerSessionManager() {
  @@ -168,6 +167,10 @@
       }
   
       public ServerSession getNewSession() {
  +     return getNewSession( null ) ;
  +    }
  +    
  +    public ServerSession getNewSession(String jsIdent) {
        if ((maxActiveSessions >= 0) &&
            (sessions.size() >= maxActiveSessions)) {
            loghelper.log( "Too many sessions " + maxActiveSessions );
  @@ -184,7 +187,7 @@
        // XXX can return MessageBytes !!!
   
   
  -     String newId= SessionIdGenerator.generateId(randomSource);
  +     String newId= SessionIdGenerator.getIdentifier(randomSource, jsIdent);
   
        // What if the newId belongs to an existing session ?
        // This shouldn't happen ( maybe we can try again ? )
  
  
  
  1.2       +33 -4     
jakarta-tomcat/src/share/org/apache/tomcat/util/threads/TimeStamp.java
  
  Index: TimeStamp.java
  ===================================================================
  RCS file: 
/home/cvs/jakarta-tomcat/src/share/org/apache/tomcat/util/threads/TimeStamp.java,v
  retrieving revision 1.1
  retrieving revision 1.2
  diff -u -r1.1 -r1.2
  --- TimeStamp.java    2000/09/25 06:10:53     1.1
  +++ TimeStamp.java    2000/11/22 00:10:00     1.2
  @@ -58,6 +58,7 @@
    */ 
   package org.apache.tomcat.util.threads;
   
  +import org.apache.tomcat.util.MessageBytes;
   import java.io.IOException;
   import java.io.ObjectInputStream;
   import java.io.ObjectOutputStream;
  @@ -68,10 +69,13 @@
   
   
   /**
  - * Marks creation and access times, plus validity.
  + * Main tool for object expiry. 
  + * Marks creation and access time of an "expirable" object,
  + * and extra properties like "id", "valid", etc.
    *
    * Used for objects that expire - originally Sessions, but 
  - * soon Contexts and Servlets ( scalability issues, large server support ).
  + * also Contexts, Servlets, cache - or any other object that
  + * expires.
    * 
    * @author Costin Manolache
    */
  @@ -82,7 +86,9 @@
       private boolean isNew = true;
       private long maxInactiveInterval = -1;
       private boolean isValid = false;
  -
  +    MessageBytes name;
  +    int id=-1;
  +    
       Object parent;
       
       public TimeStamp() {
  @@ -103,8 +109,29 @@
   
       // -------------------- Property access --------------------
   
  +    /** Return the "name" of the timestamp. This can be used
  +     *  to associate unique identifier with each timestamped object.
  +     *  The name is a MessageBytes - i.e. a modifiable byte[] or char[]. 
  +     */
  +    public MessageBytes getName() {
  +     if( name==null ) name=new MessageBytes();//lazy
  +     return name;
  +    }
  +
  +    /** Each object can have an unique id, similar with name but
  +     *  providing faster access ( array vs. hashtable lookup )
  +     */
  +    public int getId() {
  +     return id;
  +    }
  +
  +    public void setId( int id ) {
  +     this.id=id;
  +    }
  +    
       /** Returns the owner of this stamp ( the object that is
  -     *  time-stamped
  +     *  time-stamped ).
  +     *  For a 
        */
       public void setParent( Object o ) {
        parent=o;
  @@ -164,6 +191,8 @@
        maxInactiveInterval = -1;
        isNew = true;
        isValid = false;
  +     id=-1;
  +     if( name!=null) name.recycle();
       }
   
   }
  
  
  

Reply via email to