Springboot集成SpringSession

在傳統web應用中,session都是交給容器管理,但是對於分佈式或是集羣,如果交給web容器管理的話,自然是行不通的,除非是web容器共享session,但是這樣做需要入侵web容器,提高問題的複雜度,並且集羣機器之間要相互耦合。因此,springsession來了。

springSession將session從web容器中剝離出來,單獨存在服務器中。目前支持redis、database、mogonDB等。session管理責任委託給springSession承擔,當request進入web容器中時,所需的session都從springsession中獲取。

接下來實現一下:

<!-- springboot - Redis -->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-data-redis</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.session</groupId>
            <artifactId>spring-session-data-redis</artifactId>
        </dependency>
spring.redis.database=1
spring.redis.host=127.0.0.1
spring.redis.port=6379
# 連接池最大連接數
spring.redis.pool.max-active=8
spring.redis.pool.max-wait=-1
# 連接池中的最大空閒連接
spring.redis.pool.max-idle=8
# 連接池中的最小空閒連接
spring.redis.pool.min-idle=0
# 連接超時時間(毫秒)
spring.redis.timeout=3000
spring.session.store-type=redis
spring.session.redis.namespace=haozi
@GetMapping(value = "test")
    public String test(HttpServletRequest request){
        HttpSession session = request.getSession();
        User user = new User(1 , "haozi" , 18);
        session.setAttribute(session.getId() , user);

        return port + session.getId();
    }

    @GetMapping(value = "gettest")
    public String getTest(HttpServletRequest request){
        HttpSession session = request.getSession();
        String haozi = (String) session.getAttribute(session.getId());
        return haozi;
    }

在redis中通過monitor監聽看下運行數據:

publish是發佈訂閱,是springsession爲了後面刪除用戶信息用的。

再看下存的內容:

通過桌面程序可以看到結構:

其中expires沒有value,是用來做倒計時用的,倒計時結束就會把session刪掉。再看下前端響應參數:

會把存入的token存入cookie,如果想改“session”,需要加個bean

@Configuration
public class SpringSessionBeanConfiguration {
    //Cookie配置
    @Bean
    public CookieSerializer cookieSerializer(){
        DefaultCookieSerializer cookieSerializer = new DefaultCookieSerializer();
        cookieSerializer.setCookieName("user_session");//sessionId名稱
        return  cookieSerializer;
    }

    //HttpSessionId配置
    @Bean
    public HttpSessionIdResolver httpSessionIdResolver(){
        CookieHttpSessionIdResolver cookieHttpSessionIdResolver = new CookieHttpSessionIdResolver();
        cookieHttpSessionIdResolver.setCookieSerializer(cookieSerializer());
        return cookieHttpSessionIdResolver;
    }
}

再運行就變成自定義的了

具體源碼是在DefaultCookieSerializer中,可以自己去看看。

接下來總體看下源碼:

首先AbstractHttpSessionApplicationInitializer#onstartup

啓動後會在這個裏面添加監聽、過濾器,接下來進insertSessionRepositoryFilter看一下,

其中,DEFAULT_FILTER_NAME就是springSessionRepositoryFilter,將配置的filter做代理,然後註冊,那接下來進代理類看下doFilter:

通過invokeDelegate就來到了springsession下的OncePerRequestFilter:

如果是請求第一次進filter,就會進doFilterInternal方法,

 SessionRepositoryRequestWrapper和SessionRepositoryResponseWrapper封裝了很多方法,看看SessionRepositoryRequestWrapper,裏面有很多方法,對session進行了一些列的封裝。

關於cookie的sessionid的封裝,可以看CookieHttpSessionStrategy,裏面實現都很簡單,這裏就不說了。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章