• how tomcat works 读书笔记九 Session管理


    在看本文之前,请先查阅相关Session与Cookie的资料。

    这篇资料不错

    http://blog.csdn.net/fangaoxin/article/details/6952954


    Catalina通过一个叫管理器的组件来完毕 session 管理工作,该组件由org.apache.catalina.Manager interface 接口表示。一个管理器通常跟一个上下文容器相关联,它负责创建、更行以及销毁 session 对象并能给不论什么请求组件返回一个合法的 session。

    Session对象

    uml图例如以下:



    看上图,我们知道我们使用的session事实上是javax.servlet.http.HttpSession接口的实现对象。
    又看到了Facade,门面模式,为什么会有它呢?标准session的一些属性功能须要对外部类隐藏,所以就有了一个facade类,对他做一些包装;有一些方法标准session里有,而标准sessionfacade里就没有,比如org.apache.catalina.Session接口里的方法。
    细致看这两个类,StandardSessionFacade与StandardSession。
    我们非常清楚StandardSessionFacade里面应该有一个StandardSession的引用。
    只是我有点不明确为什么StandardSession里面另一个StandardSessionFacade的引用?
    看了凝视大概明确了:
         StandardSession.java
        /**
         * The facade associated with this session.  NOTE:  This value is not
         * included in the serialized version of this object.
         */
        private transient StandardSessionFacade facade = null;
    
    Catalina通过一个叫session管理器的组件来管理建立的Session对象,该组件由org.apache.catalina.Manager接口表示。Session管理器与一个Context级别的容器相关联。


    Manager

    Session管理器组件负责管理Session对象,比如创建和删除Session对象。在catalina中,ManagerBase是一个工具类,提供了最主要的一些功能。


    当中,StandardManager将session保存在内存里,PersistentManagerBase将session持久化到文件或数据库中(在本文中,我们仅仅介绍StandardManager)

    应用程序:

    先看我们的演示样例程序:
    在Bootstrap里,连接器启动之前加上以下的代码;
        // add a Manager
        Manager manager = new StandardManager();
        context.setManager(manager);
    我们的servlet例如以下:
    import javax.servlet.ServletException;
    import javax.servlet.http.HttpServlet;
    import javax.servlet.http.HttpServletRequest;
    import javax.servlet.http.HttpServletResponse;
    import javax.servlet.http.HttpSession;
    import java.io.IOException;
    import java.io.PrintWriter;
    
    public class SessionServlet extends HttpServlet {
    
        private static final long serialVersionUID = -446310114281616885L;
    
    public void doGet(HttpServletRequest request, HttpServletResponse response)
        throws ServletException, IOException {
        System.out.println("SessionServlet -- service");
        response.setContentType("text/html");
        PrintWriter out = response.getWriter();
        out.println("<html>");
        out.println("<head><title>SessionServlet</title></head>");
        out.println("<body>");
        String value = request.getParameter("value");
        HttpSession session = request.getSession(true);
        out.println("<br>the previous value is " +
          (String) session.getAttribute("value"));
        out.println("<br>the current value is " + value);
        session.setAttribute("value", value);
        out.println("<br><hr>");
        out.println("<form>");
        out.println("New Value: <input name=value>");
        out.println("<input type=submit>");
        out.println("</form>");
        out.println("</body>");
        out.println("</html>");
      }
    }
    编译好的servletclass文件放在什么地方,还用我说吗?假设不知道就先看看前面几章吧。

    先上终于的结果图:

    先输入33然后15最后57的效果图



    这是从SessionServlet開始的时序图:


    在HttpRequestBase类中的doGetSession()方法中会首先推断requestedSessionId是否为null,假设为null,才会调用manager.createSession()...
    如今就有一个问题,那这个requestedSessionId是怎么来的?
    事实上在本书第三章连接器那里,解析cookid的地方
    parseHeaders方法下:
          if (name.equals("cookie")) {
            Cookie cookies[] = RequestUtil.parseCookieHeader(value);
            for (int i = 0; i < cookies.length; i++) {
              if (cookies[i].getName().equals("jsessionid")) {
                // Override anything requested in the URL
                if (!request.isRequestedSessionIdFromCookie()) {
                  // Accept only the first session id cookie
                  request.setRequestedSessionId(cookies[i].getValue());
                  request.setRequestedSessionCookie(true);
                  request.setRequestedSessionURL(false);
                }
              }
              request.addCookie(cookies[i]);
            }
          }
    第一次请求SessionServlet的时候,自然没有jsessionid,RequestedSessionId也为空,就要manager.createSession()
    第二回的时候,浏览器在Cookie里面增加了jsessionid这一项,因此后面
         if (requestedSessionId != null) {
                try {
                    session = manager.findSession(requestedSessionId);
                } catch (IOException e) {
                    session = null;
                }
                if ((session != null) && !session.isValid())
                    session = null;
                if (session != null) {
                    return (session.getSession());
                }
            }

  • 相关阅读:
    Visual Studio ------ 多项目启动
    windows ------ 系统激活 win10
    Java ----- 递归与迭代
    SpringCloud:初识(微服务与SpringCloud)
    The server time zone value '&#214;&#208;&#185;&#250;&#177;&#234;&#215;&#188;&#202;&#177;&#188;&#228;' is unrecognized or represents more than one time zone.
    Solr:SolrJ(增删改查)
    Solr:后台管理界面的使用(管理索引库、导入数据库数据、查询)
    Solr:Slor初识(概述、Windows版本的安装、添加IK分词器)
    Vue:v-model的使用
    Vue:循环遍历(v-for)
  • 原文地址:https://www.cnblogs.com/mfrbuaa/p/4301591.html
Copyright © 2020-2023  润新知