作 Java Web 開發的人多數都會須要使用到 session (會話),咱們使用 session 來保存一些須要在兩個不一樣的請求之間共享數據。通常 Java 的 Web 容器像 Tomcat、Resin、Jetty 等等,它們會在內存中保存 session 數據。這樣作會有兩個不足:css
咱們以使用比例最高的 Tomcat 爲例,針對第二個問題 Tomcat 提供了集羣 session 複製的解決方案,詳情請看官方文檔。看完文檔你會發現 Tomcat 自帶的方法配置很是複雜,並且它沒有解決第一個問題 —— 服務重啓致使 session 數據丟失的問題。html
如今還有另一種方案就是使用 memcached 或者是 redis 來存儲 session 數據,因而就有了這麼一些開源項目:java
這些開源項目使用和配置都比較簡單,並且對應用徹底透明,只須要在 server.xml 中配置好 Manager 便可。例如:git
<Context> ... <Manager className="de.javakaffee.web.msm.MemcachedBackupSessionManager" memcachedNodes="n1:host1.yourdomain.com:11211,n2:host2.yourdomain.com:11211" sticky="false" sessionBackupAsync="false" lockingMode="uriPattern:/path1|/path2" requestUriIgnorePattern=".*\.(ico|png|gif|jpg|css|js)$" transcoderFactoryClass="de.javakaffee.web.msm.serializer.kryo.KryoTranscoderFactory" /> </Context>
可是這幾個開源項目都有一個最根本的問題無法解決,當存放在 session 中的數據量比較大,並且讀取 session 數據很是頻繁時會致使 memcached 或者是 redis 吞吐量受帶寬限制使得性能變得很是差。逼迫你必須經過 memcached 或者 redis 的擴容和集羣來解決問題,大大的增長了硬件投入的成本和運維的成本。web
--------redis
那麼用 J2Cache 的 session-manager 模塊就能夠有效解決前面提到的全部問題。J2Cache 在 redis 的基礎上引入了內存緩存的概念,能夠確保服務重啓後 session 數據不會丟失,其次極大的下降了 redis 的數據吞吐量,保證在高併發狀況下依然有很好的性能表現。apache
與前面提到的幾個開源項目不一樣,J2Cache 的 session manager 採用 Filter 方式實現,支持各類 Java 的 Web 容器服務。緩存
使用方法:tomcat
1. Web 項目添加 J2Cache 的 session-manager 模塊依賴:cookie
<dependency> <groupId>net.oschina.j2cache</groupId> <artifactId>j2cache-session-manager</artifactId> <version>1.0.0-beta4</version> </dependency>
2. 在 web.xml 中配置 Filter:
<filter> <filter-name>j2cache-session-filter</filter-name> <filter-class>net.oschina.j2cache.session.J2CacheSessionFilter</filter-class> <init-param><!-- 內存中存放會話數 --> <param-name>session.maxSizeInMemory</param-name> <param-value>2000</param-value> </init-param> <init-param><!-- 會話有效期,單位:秒鐘 --> <param-name>session.maxAge</param-name> <param-value>1800</param-value> </init-param> <!-- cookie configuration --> <init-param> <param-name>cookie.name</param-name> <param-value>J2CACHE_SESSION_ID</param-value> </init-param> <init-param> <param-name>cookie.path</param-name> <param-value>/</param-value> </init-param> <init-param> <param-name>cookie.domain</param-name> <param-value></param-value> </init-param> <!-- redis configuration --> <init-param> <param-name>redis.mode</param-name> <param-value>single</param-value> </init-param> <init-param> <param-name>redis.hosts</param-name> <param-value>127.0.0.1:6379</param-value> </init-param> <init-param> <param-name>redis.channel</param-name> <param-value>j2cache</param-value> </init-param> <init-param> <param-name>redis.cluster_name</param-name> <param-value>j2cache</param-value> </init-param> <init-param> <param-name>redis.timeout</param-name> <param-value>2000</param-value> </init-param> <init-param> <param-name>redis.password</param-name> <param-value></param-value> </init-param> <init-param> <param-name>redis.database</param-name> <param-value>0</param-value> </init-param> <init-param> <param-name>redis.maxTotal</param-name> <param-value>100</param-value> </init-param> <init-param> <param-name>redis.maxIdle</param-name> <param-value>10</param-value> </init-param> <init-param> <param-name>redis.minIdle</param-name> <param-value>1</param-value> </init-param> </filter> <filter-mapping> <filter-name>j2cache-session-filter</filter-name> <url-pattern>/*</url-pattern> </filter-mapping>
3. 啓動應用,便可開啓分佈式 session 存儲。
當重啓 Web 應用時,內存中的 session 數據爲空,會自動從 redis 中讀取重啓前保存的 session 數據。全部節點又經過 redis 進行 session 數據的共享,當有 session 數據更新時會經過 Redis Pub/Sub 來通知其餘節點從新從 Redis 中讀取數據,確保不一樣節點的 session 數據是一致的。
sesson-manager 模塊代碼 https://gitee.com/ld/J2Cache/tree/master/modules/session-manager
很簡單吧? 去 https://gitee.com/ld/J2Cache 點個贊吧?