tomcat会话之持久化会话管理器

前面提到的标准会话管理器已经提供了基础的会话管理功能,但在持久化方面做得还是不够,或者说在某些情景下无法满足要求,例如把会话以文件或数据库形式存储到存储介质中,这些都是标准会话管理器无法做到的,于是另外一种会话管理器被设计出来——持久化会话管理器。

在分析持久化会话管理器之前不妨先了解另外一个抽象概念会话存储设备Store,引入这个概念是为了更清晰方便地实现各种会话存储方式。作为存储设备最重要的操作无非就是读写操作,读即是将会话从存储设备加载到内存中,而写则将会话写入存储设备中,所以定义了两个重要的方法load和save与之相对应。FileStore和JDBCStore只要扩展Store接口各自实现load和save方法即可分别实现以文件或数据库形式存储会话。UML类图如下所示:

 

1) FileStore

文件存储设备提供的是以文件形式保存会话,在写入时会针对每个会话生成一个文件用于保存此会话的相关信息,每个会话文件名被定义为sessionId+”.session”的格式,例如“326257DA6DB76F8D2E38F2C4540D1DEA.session”,而存放目录路径则由ServletContext.TEMPDIR变量指定,一般默认目录路径为”%CATALINA_HOME%/work/Catalina/localhost/web’name/”,其实就是”tomcat安装根目录+work+engineName+hostName+contextName”。所以假如有一万个会话则会有一万个会话文件。为了方便操作写入直接使用jdk自带的java.io.ObjectOutputStream对会话对象进行序列化并写入文件,所以有一点需要注意的是所有会话中的对象必须实现Serializable接口。

类似的,加载会话是通过传入一个sessionId,拼装成sessionId+”.session”格式的文件名去找对应的会话文件,然后使用jdk自带的java.io.ObjectInputStream将会话对象载入内存中,其实就是一个反序列化过程。

配置文件可以按如下配置:

<Store className="org.apache.catalina.session.FileStore" directory="sessiondir"/>

如果配置了directory,则将以”%CATALINA_HOME%/work/Catalina/localhost/web’name/sessiondir”为存放目录,当然如果配置为绝对路径则以你配置的绝对路径为存放目录。

以FileStore为存储设备使用时看起来在文件操作IO上效率相当低,因为对每个文件操作都是打开-操作-关闭,并未使用任何优化措施,所以tomcat在选择使用此方式时这里很可能会成为影响整体性能的一个点,必须要做好充分的性能测试。

2) JDBCStore

JDBC存储设备提供的是以数据库形式存放会话,后端可以是任意厂商的数据库,只要有对应的数据库驱动程序即可。既然要存放数据肯定就要先在数据库中创建一张会话表,表的结构必须要tomcat与mysql双方约定好,例如tomcat默认的表名为”tomcat$sessions”,表字段一共有6个,分别为”app”、”id”、”data”、”valid”、”maxinactive”、”lastaccess”,app字段用于区分哪个web应用,id字段即会话标识,data字段用于存放会话对象字节串,valid字段表示此会话是否有效,maxinactive字段表示最大存活时间,lastaccess字段表示最后访问时间。其中需要注意的是data字段,由于它的大小直接影响会话对象的大小,所以需要根据实际设置它的类型,如果是mysql可以考虑设置为Blob(65k)或MediumBlob(16m)。

这样一来,会话的加载和保存其实就转化为对数据库的读写操作了,而获取数据库连接的逻辑是先判断tomcat容器中是否有数据源,如果有则从数据源中直接获取一条连接使用,但是如果没有的话则会自己通过驱动去创建连接,需要注意的是从数据源中获取的连接在使用完后会放回数据源中,但自己通过驱动创建的连接使用完则不会关闭,这个很好理解,因为数据源是一个池,重新获取连接很快,而自建的连接重新创建一般需要秒级别的消耗,明显会造成大问题。

下面以mysql数据库为例配置一个JDBC存储设备:

    <Store className="org.apache.catalina.session.JDBCStore"                

       connectionURL="jdbc:mysql://localhost:3306/web_session?user=user&password=password"

       driverName="com.mysql.jdbc.Driver"

       sessionAppCol="app_name"

       sessionDataCol="session_data"

       sessionIdCol="session_id"

       sessionLastAccessedCol="last_access"

       sessionMaxInactiveCol="max_inactive"

       sessionTable="tomcat_sessions"

       sessionValidCol="valid_session" />

其中关于会话表及其字段的一些属性可以不必配置,直接采用tomcat默认的即可,但驱动程序及连接url则一定要配置。

以JDBCStore为存储设备时从表面看起来并不会有明显的IO性能问题,因为它使用数据源获取连接,是一种池化技术,就算不存在数据源也是采用长久连接模式,一般数据流不是非常大的话都不会存在性能问题。

整个介绍完存储设备store后接着看持久化会话管理器,其实持久化会话管理器主要实现的就是三种逻辑下的对会话进行持久化操作,①当会话对象数量超过指定阀值时则将超出的会话对象转换出(保存到store中并把内存中的此对象删除)到store中;②当会话空闲时间超过指定阀值时则将此会话对象换出;③当会话空闲时间超过指定阀值时则将此会话进行备份(保存到store中并且内存还存在此对象)。

实现上面的逻辑只需对所有会话集合进行遍历即可,把符合条件的通过store保存。由于有些会话被持久化到store中,所以通过id查找会话时需先从内存中查找再往store查找。

下面是一个配置例子,会话数大于1000时则将空闲时间大于60秒的会话转移到store直到会话数量控制在1000,超过120秒空闲的会话被换出到store,超过180秒空闲的会话将备份到store。

<Manager className="org.apache.catalina.session.PersistentManager" 

    maxActiveSessions="1000"

    minIdleSwap="60"

    maxIdleSwap="120"

    maxIdleBackup="180">

    <Store className="org.apache.catalina.session.FileStore" directory="sessiondir"/>

 </Manager>

所以在了解了两种Store后对持久化会话管理器的实现原理机制就相当清楚了,其实就是提供两种会话保存方式并提供管理这些会话的操作,它提高了tomcat状态处理相关方面的容错能力得到提升。

 

点击订购作者《Tomcat内核设计剖析》

时间: 2024-07-28 13:53:05

tomcat会话之持久化会话管理器的相关文章

集群增量会话管理器——DeltaManager

DeltaManager会话管理器是tomcat默认的集群会话管理器,它主要用于集群中各个节点之间会话状态的同步维护,由于相关内容涉及到集群,可能会需要一些集群通信相关知识,如果有疑问可结合集群相关章节. 集群增量会话管理器的职责是将某节点的会话该变同步到集群内其他成员节点上,它属于全节点复制模式,所谓全节点复制是指集群中某个节点的状态变化后需要同步到集群中剩余的节点,非全节点方式可能只是同步到其中某个或若干节点.在集群中全节点会话复制的一个大致步骤如下图所示,客户端发起一个请求,假设通过一定的

标准会话管理器——StandardManager

用于保存状态的会话对象已经有了,现在就需要一个管理器来管理所有会话,例如会话id生成.根据会话id找出对应的会话.对于过期的会话进行销毁等等操作.用一句话描述标准会话管理器:提供一个专门管理某个web应用所有会话的容器,并且会在web应用启动停止时刻进行会话重加载和持久化. 会话管理主要提供的功能包括会话ID生成器.后台处理(处理过期会话).持久化模块及会话集的维护.   首先看会话ID生成器,它负责为每个会话生成分配一个唯一标识,例如最终会生成类似"326257DA6DB76F8D2E38F2

基于会话的探索性测试管理

探索性测试是一个特殊的测试过程,它的测试活动和测试内容是动态变化的,更多的是通过测试执行的结果来指导后续的测试活动,花在文档上的时间很少,这也就意味着探索性测试的可管理性不强,对于每个测试人员执行的测试活动的进度和效果很难监控.为了更好地开展探索性测试,Jonathan Bach提出了一种"基于会话的测试管理(Session-basedtest management,缩写为SBTM)"方法,这种方法可以对探索性测试进行更好地管理,把探索性测试的优势更好地发挥出来. 基于会话的测试管理是

shiro和spring集成时session管理器超时时间问题

问题描述 shiro和spring集成时session管理器超时时间问题 这是我的配置文件,我配置了并发人数控制和动态权限过滤,然后session超时时间这里也是配置了的,然后并没有什么鸟用,在登录以后获取超时时间也是正常的,但还是1分钟就过期了. <?xml version="1.0" encoding="UTF-8"?> xmlns:util="http://www.springframework.org/schema/util"

ASP.NET 中 Session 实现原理浅析 [2] 状态管理器

asp.net|session 状态管理本来是一件很美好的事情,嘿嘿,只可惜总是有些厂商在实现的时候考虑得不那么周全.例如 MS 在 ASP 中的状态管理实现就比较烂,因为只实现了一个进程内的基于内存的状态管理,故而存在很多问题: 1.所有的 Session 数据都保存在 Web 服务的进程中,会造成服务器支持会话数量受到服务器内存资源的限制问题,同时也因为大量非活动会话导致内存被无效占用. 2.服务器进程崩溃会导致所有的会话数据丢失. 3.会话无法跨进程或在负载均衡情况下使用,除非负载均衡技术

[翻译] SoundManager 音频管理器

SoundManager 音频管理器 https://github.com/nicklockwood/SoundManager Purpose SoundManager is a simple class for playing sound and music in iOS or Mac apps. SoundManager是一个简单的用来播放音乐的类.   Supported OS & SDK Versions Supported build target - iOS 7.0 / Mac OS

Alpine Linux 之漏洞利用(二):软件包管理器漏洞分析

本文讲的是Alpine Linux 之漏洞利用(二):软件包管理器漏洞分析, 在Alpine Linux 漏洞利用的第一部分<Alpine Linux:从漏洞发现到代码执行>,我对Alpine Linux的软件包管理器中的两个关键漏洞, CVE-2017-9669和CVE-2017-9671做了深入的分析. 今天这部分,我会对这两个漏洞的发现过程进行详细描述,并演示如何实现远程执行代码. 第一步是把部署环境中导致 漏洞的所有内容都进行复制,由于这是一个可用性测试(sanity check),所

《实施Cisco统一通信管理器(CIPT1)》——1.2 CUCM概述

1.2 CUCM概述 实施Cisco统一通信管理器(CIPT1) Cisco UC(统一通信)是基于IP的通信系统,它集成了语音.视频.数据以及移动产品和应用.这一系统能够实现更加高效而又安全的通信,并且能够改变人们的通信方式.UC的出现与电报的产生一样,都代表了通信方式的根本性变革.UC通过将语音.视频和数据相集成,为高效通信消除了地域阻碍.技术的发展和进步也会使业务变得更加流畅.对于那些我们早已触手可得的信息,UC能够将其共享,从而建立知识体系并创造价值. Cisco UC是集成化解决方案的

《实施Cisco统一通信管理器(CIPT1)》一1.2 CUCM概述

1.2 CUCM概述 实施Cisco统一通信管理器(CIPT1) Cisco UC(统一通信)是基于IP的通信系统,它集成了语音.视频.数据以及移动产品和应用.这一系统能够实现更加高效而又安全的通信,并且能够改变人们的通信方式.UC的出现与电报的产生一样,都代表了通信方式的根本性变革.UC通过将语音.视频和数据相集成,为高效通信消除了地域阻碍.技术的发展和进步也会使业务变得更加流畅.对于那些我们早已触手可得的信息,UC能够将其共享,从而建立知识体系并创造价值. Cisco UC是集成化解决方案的