sessionmanager.java

来自「RESIN 3.2 最新源码」· Java 代码 · 共 1,493 行 · 第 1/3 页

JAVA
1,493
字号
  }  /**   * Returns the session store.   */  public Store getSessionStore()  {    return _sessionStore;  }  /**   * Returns true if the session exists in this manager.   */  public boolean containsSession(String id)  {    return _sessions.get(id) != null;  }  /**   * Create a new session.   *   * @param oldId the id passed to the request.  Reuse if possible.   * @param now the current date   * @param sessionGroup the srun index for this machine   */  public SessionImpl createSession(String oldId, long now,                                   HttpServletRequest request,				   boolean fromCookie)  {    String id = oldId;    if (id == null || id.length() < 4        || ! reuseSessionId(fromCookie)) {      // server/0175      // || ! _objectManager.isInSessionGroup(id)            id = createSessionId(request, true);    }    SessionImpl session = create(id, now, true);    if (session == null)      return null;    session.addUse();    synchronized (_statisticsLock) {      _sessionCreateCount++;    }    synchronized (session) {      if (_sessionStore != null && id.equals(oldId))        load(session, now, true);      else	session.create(now, true);    }    // after load so a reset doesn't clear any setting    handleCreateListeners(session);        return session;  }  /**   * Creates a pseudo-random session id.  If there's an old id and the   * group matches, then use it because different webApps on the   * same matchine should use the same cookie.   *   * @param sessionGroup possibly assigned by the web server   */  public String createSessionId(HttpServletRequest request)  {    return createSessionId(request, false);  }  /**   * Creates a pseudo-random session id.  If there's an old id and the   * group matches, then use it because different webApps on the   * same machine should use the same cookie.   *   * @param sessionGroup possibly assigned by the web server   */  public String createSessionId(HttpServletRequest request,                                boolean create)  {    String id;    do {      id = createSessionIdImpl(request);    } while (create && getSession(id, 0, create, true) != null);    if (id == null || id.equals(""))      throw new RuntimeException();    return id;  }  public String createSessionIdImpl(HttpServletRequest request)  {    StringBuilder sb = new StringBuilder();    // this section is the host specific session index    // the most random bit is the high bit    int index = _selfIndex;    // look at caucho.session-server-id for a hint of the owner    Object owner = request.getAttribute("caucho.session-server-id");    if (owner == null) {    }    else if (owner instanceof Number) {      index = ((Number) owner).intValue();    }    else if (owner instanceof String) {      ClusterServer server = _cluster.getServer((String) owner);      if (server != null)	index = server.getIndex();    }    if (index < 0)      index = 0;    _cluster.generateBackup(sb, index);    int length = _cookieLength;    length -= sb.length();    long random = RandomUtil.getRandomLong();    for (int i = 0; i < 11 && length-- > 0; i++) {      sb.append(convert(random));      random = random >> 6;    }    if (length > 0) {      long time = Alarm.getCurrentTime();      for (int i = 0; i < 7 && length-- > 0; i++) {        sb.append(convert(time));        time = time >> 6;      }    }    while (length > 0) {      random = RandomUtil.getRandomLong();      for (int i = 0; i < 11 && length-- > 0; i++) {        sb.append(convert(random));        random = random >> 6;      }    }    if (_isAppendServerIndex) {      sb.append('.');      sb.append((index + 1));    }    return sb.toString();  }  /**   * Returns a session from the session store, returning null if there's   * no cached session.   *   * @param key the session id   * @param now the time in milliseconds   *   * @return the cached session.   */  public SessionImpl getSession(String key, long now,				boolean create, boolean fromCookie)  {    SessionImpl session;    boolean isNew = false;    boolean killSession = false;    if (_sessions == null)      return null;    session = _sessions.get(key);    if (session != null && ! session.getId().equals(key))      throw new IllegalStateException(key + " != " + session.getId());    if (now <= 0) // just generating id      return session;    if (session != null && ! session.addUse()) {      session = null;    }    if (session == null && _sessionStore != null) {      if (! _objectManager.isInSessionGroup(key))	return null;      session = create(key, now, create);      if (! session.addUse())	session = null;      isNew = true;    }    if (session == null)      return null;        if (isNew) {      killSession = ! load(session, now, create);      isNew = killSession;    }    else if (! session.load()) {      // if the load failed, then the session died out from underneath      session.reset(now);      isNew = true;    }    if (killSession && (! create || ! reuseSessionId(fromCookie))) {      // XXX: session.setClosed();      session.endUse();      _sessions.remove(key);      // XXX:      session._isValid = false;              return null;    }    else if (isNew)      handleCreateListeners(session);    else      session.setAccess(now);        return session;  }  /**   * Creates a session.  It's already been established that the   * key does not currently have a session.   */  private SessionImpl create(String key, long now, boolean isCreate)  {    SessionImpl session = new SessionImpl(this, key, now);    /*    Store sessionStore = _sessionStore;    if (sessionStore != null) {      ClusterObject clusterObject = sessionStore.createClusterObject(key);      session.setClusterObject(clusterObject);    }     */    // If another thread has created and stored a new session,    // putIfNew will return the old session    session = _sessions.putIfNew(key, session);    if (! key.equals(session.getId()))      throw new IllegalStateException(key + " != " + session.getId());    return session;  }  /**   * Notification from the cluster.   */  public void notifyRemove(String id)  {    SessionImpl session = _sessions.get(id);    if (session != null)      session.invalidateRemote();  }  private void handleCreateListeners(SessionImpl session)  {    if (_listeners != null) {      HttpSessionEvent event = new HttpSessionEvent(session);            for (int i = 0; i < _listeners.size(); i++) {        HttpSessionListener listener = _listeners.get(i);        listener.sessionCreated(event);      }    }  }  /**   * Loads the session from the backing store.  The caller must synchronize   * the session.   *   * @param session the session to load.   * @param now current time in milliseconds.   */  private boolean load(SessionImpl session, long now, boolean isCreate)  {    try {      // XXX: session.setNeedsLoad(false);      /*      if (session.getUseCount() > 1) {	// if used by more than just us, 	return true;      }      else*/ if (now <= 0) {        return false;      }      else if (session.load()) {        session.setAccess(now);        return true;      }      else {        session.create(now, isCreate);      }    } catch (Exception e) {      log.log(Level.FINE, e.toString(), e);      session.reset(now);    }        return false;  }  /**   * Adds a session from the cache.   */  void addSession(SessionImpl session)  {    _sessions.put(session.getId(), session);  }  /**   * Removes a session from the cache.   */  void removeSession(SessionImpl session)  {    _sessions.remove(session.getId());  }  /**   * Timeout for reaping old sessions   *   * @return number of live sessions for stats   */  public void handleAlarm(Alarm alarm)  {    try {      _sessionList.clear();      int liveSessions = 0;      if (_isClosed)	return;      long now = Alarm.getCurrentTime();      long accessWindow = 0;      if (_sessionStore != null)	accessWindow = _sessionStore.getAccessWindowTime();            synchronized (_sessions) {	_sessionIter = _sessions.values(_sessionIter);	while (_sessionIter.hasNext()) {	  SessionImpl session = _sessionIter.next();	  long maxIdleTime = session._maxInactiveInterval + accessWindow;	  if (session.inUse())	    liveSessions++;	  else if (session._accessTime + maxIdleTime < now)	    _sessionList.add(session);	  else	    liveSessions++;	}      }            synchronized (_statisticsLock) {	_sessionTimeoutCount += _sessionList.size();      }      for (int i = 0; i < _sessionList.size(); i++) {	SessionImpl session = _sessionList.get(i);	try {	  if (! session.isValid())	    continue;	  if (_storeManager == null) {	    // if no persistent store then invalidate	    // XXX: server/12cg - single signon shouldn't logout     	    session.invalidateTimeout();	  }	  else if (session.getSrunIndex() != _selfIndex && _selfIndex >= 0) {            if (log.isLoggable(Level.FINE))              log.fine(session + " timeout (backup)");            	    // if not the owner, then just remove	    _sessions.remove(session.getId());	  }	  else {	    session.invalidateTimeout();	  }	} catch (Throwable e) {	  log.log(Level.FINE, e.toString(), e);	}      }    } finally {      if (! _isClosed)	_alarm.queue(60000);    }  }  /**   * Cleans up the sessions when the WebApp shuts down gracefully.   */  public void close()  {    synchronized (this) {      if (_isClosed)        return;      _isClosed = true;    }    if (_sessions == null)      return;    _alarm.dequeue();        ArrayList<SessionImpl> list = new ArrayList<SessionImpl>();        boolean isError = false;    // XXX: messy way of dealing with saveOnlyOnShutdown    synchronized (_sessions) {      _sessionIter = _sessions.values(_sessionIter);      while (_sessionIter.hasNext()) {        SessionImpl session = _sessionIter.next();        if (session.isValid())          list.add(session);      }      // XXX: if cleared here, will remove the session      // _sessions.clear();    }    for (int i = list.size() - 1; i >= 0; i--) {      SessionImpl session = list.get(i);            if (log.isLoggable(Level.FINE))        log.fine("close session " + session.getId());            try {        if (session.isValid()) {          synchronized (session) {	    // server/016i, server/018x	    if (! session.isEmpty())	      session.saveOnShutdown();          }        }        _sessions.remove(session.getId());      } catch (Exception e) {        if (! isError)          log.log(Level.WARNING, "Can't store session: " + e, e);        isError = true;      }    }    if (_admin != null)      _admin.unregister();    _sessionList = new ArrayList<SessionImpl>();    /*    if (_clusterManager != null)      _clusterManager.removeContext(_distributionId);    */  }  /**   * Converts an integer to a printable character   */  private static char convert(long code)  {    code = code & 0x3f;        if (code < 26)      return (char) ('a' + code);    else if (code < 52)      return (char) ('A' + code - 26);    else if (code < 62)      return (char) ('0' + code - 52);    else if (code == 62)      return '_';    else      return '-';  }  @Override  public String toString()  {    return getClass().getSimpleName() + "[" + _webApp.getContextPath() + "]";  }}

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?