上一篇文章介紹了一些Session和Cookie的基礎知識,這篇文章開始正式介紹Spring Session是如何對傳統的Session進行改造的。官網這么介紹Spring Session:

其具體的特性非常之多,具體的內容可以從文檔中了解到,筆者做一點自己的總結,Spring Session的特性包括但不限于以下:
使用GemFire來構建C/S架構的httpSession(不關注)
使用第三方倉儲來實現集群session管理,也就是常說的分布式session容器,替換應用容器(如tomcat的session容器)。倉儲的實現,Spring Session提供了三個實現(redis,mongodb,jdbc),其中redis使我們最常用的。程序的實現,使用AOP技術,幾乎可以做到透明化地替換。(核心)
可以非常方便的擴展Cookie和自定義Session相關的Listener,Filter。
可以很方便的與Spring Security集成,增加諸如findSessionsByUserName,rememberMe,限制同一個賬號可以同時在線的Session數(如設置成1,即可達到把前一次登錄頂掉的效果)等等
介紹完特性,下面開始一步步集成Spring Session
## 使用Redis集成Spring Session
* 引入依賴,Spring Boot的版本采用1.5.4
~~~
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.session</groupId>
<artifactId>spring-session-data-redis</artifactId>
</dependency>
~~~
* 配置
配置類開啟Redis Http Session
~~~
@Configuration
@EnableRedisHttpSession
public class HttpSessionConfig {
}
~~~
基本是0配置,只需要讓主配置掃描到@EnableRedisHttpSession即可
配置文件application.yml,配置連接的redis信息
~~~
spring:
redis:
host: localhost
port: 6379
database: 0
~~~
* 編寫測試Controller,以便于觀察Spring Session的特性,和前一篇文章使用同樣的代碼
* 啟動類省略,下面開始測試
在瀏覽器中訪問如下端點:http://localhost:8080/test/cookie?browser=chrome , 下面是連續訪問4次的結果
~~~
1 不存在session,設置browser=chrome
2 存在session,browser=chrome
SESSION : 70791b17-83e1-42db-8894-73fbd2f2a159
3 存在session,browser=chrome
SESSION : 70791b17-83e1-42db-8894-73fbd2f2a159
4 存在session,browser=chrome
SESSION : 70791b17-83e1-42db-8894-73fbd2f2a159
~~~
如果還記得上一篇文章中運行結果的話,會發現和原生的session管理是有一些差別,原先的信息中我們記得Cookie中記錄的Key值是JSESSIONID,而替換成RedisHttpSession之后變成了SESSION。接著觀察redis中的變化:

解析一下這個redis store,如果不糾結于細節,可以跳過,不影響使用。
?1 spring:session是默認的Redis HttpSession前綴(redis中,我們常用’:’作為分割符)。
2 每一個session都會有三個相關的key,第三個key最為重要,它是一個HASH數據結構,將內存中的session信息序列化到了redis中。如上文的browser,就被記錄為sessionAttr:browser=chrome,還有一些meta信息,如創建時間,最后訪問時間等。
3 另外兩個key,expirations:1504446540000和sessions:expires:7079…我發現大多數的文章都沒有對其分析,前者是一個SET類型,后者是一個STRING類型,可能會有讀者發出這樣的疑問,redis自身就有過期時間的設置方式TTL,為什么要額外添加兩個key來維持session過期的特性呢?這需要對redis有一定深入的了解才能想到這層設計。當然這不是本節的重點,簡單提一下:redis清除過期key的行為是一個異步行為且是一個低優先級的行為,用文檔中的原話來說便是,可能會導致session不被清除。于是引入了專門的expiresKey,來專門負責session的清除,包括我們自己在使用redis時也需要關注這一點。在開發層面,我們僅僅需要關注第三個key就行了。
## 總結
本節主要講解了Spring Boot如何集成Spring Session,下一節將介紹更加復雜的特性。包括自定義Cookie序列化策略,與Spring Security的集成,根據用戶名查找session等特性以及使用注意點。
- java
- 設計模式
- 設計模式總覽
- 設計原則
- 工廠方法模式
- 抽象工廠模式
- 單例模式
- 建造者模式
- 原型模式
- 適配器模式
- 裝飾者模式
- 代理模式
- 外觀模式
- 橋接模式
- 組合模式
- 享元模式
- 策略模式
- 模板方法模式
- 觀察者模式
- 迭代子模式
- 責任鏈模式
- 命令模式
- 備忘錄模式
- 狀態模式
- 訪問者模式
- 中介者模式
- 解釋器模式
- 附錄
- JVM相關
- JVM內存結構
- Java虛擬機的內存組成以及堆內存介紹
- Java堆和棧
- 附錄-數據結構的堆棧和內存分配的堆區棧區的區別
- Java內存之Java 堆
- Java內存之虛擬機和內存區域概述
- Java 內存之方法區和運行時常量池
- Java 內存之直接內存(堆外內存)
- JAVA內存模型
- Java內存模型介紹
- 內存模型如何解決緩存一致性問題
- 深入理解Java內存模型——基礎
- 深入理解Java內存模型——重排序
- 深入理解Java內存模型——順序一致性
- 深入理解Java內存模型——volatile
- 深入理解Java內存模型——鎖
- 深入理解Java內存模型——final
- 深入理解Java內存模型——總結
- 內存可見性
- JAVA對象模型
- JVM內存結構 VS Java內存模型 VS Java對象模型
- Java的對象模型
- Java的對象頭
- HotSpot虛擬機
- HotSpot虛擬機對象探秘
- 深入分析Java的編譯原理
- Java虛擬機的鎖優化技術
- 對象和數組并不是都在堆上分配內存的
- 垃圾回收
- JVM內存管理及垃圾回收
- JVM 垃圾回收器工作原理及使用實例介紹
- JVM內存回收理論與實現(對象存活的判定)
- JVM參數及調優
- CMS GC日志分析
- JVM實用參數(一)JVM類型以及編譯器模式
- JVM實用參數(二)參數分類和即時(JIT)編譯器診斷
- JVM實用參數(三)打印所有XX參數及值
- JVM實用參數(四)內存調優
- JVM實用參數(五)新生代垃圾回收
- JVM實用參數(六) 吞吐量收集器
- JVM實用參數(七)CMS收集器
- JVM實用參數(八)GC日志
- Java性能調優原則
- JVM 優化經驗總結
- 面試題整理
- 面試題1
- java日志規約
- Spring安全
- OAtuth2.0簡介
- Spring Session 簡介(一)
- Spring Session 簡介(二)
- Spring Session 簡介(三)
- Spring Security 簡介(一)
- Spring Security 簡介(二)
- Spring Security 簡介(三)
- Spring Security 簡介(四)
- Spring Security 簡介(五)
- Spring Security Oauth2 (一)
- Spring Security Oauth2 (二)
- Spring Security Oauth2 (三)
- SpringBoot
- Shiro
- Shiro和Spring Security對比
- Shiro簡介
- Session、Cookie和Cache
- Web Socket
- Spring WebFlux