【SpringBoot】spring-session-data-redis 解決集群環境下session共享


為什么會產生Session共享問題

  集群情況下,session保存在各自的服務器的tomcat中,當分發地址至不同服務時,導致sesson取不到,就會產生session共享問題。

解決方案

  • 負載均衡中,IP綁定策略。如nginx:ip_hash
  • tomcat的session共享
    •   優點:不需要額外開發,只需搭建tomcat集群即可
    •   缺點:tomcat 是全局session復制,集群內每個tomcat的session完全同步(也就是任何時候都完全一樣的) 在大規模應用的時候,用戶過多,集群內tomcat數量過多,session的全局復制會導致集群性能下降, 因此,tomcat的數量不能太多,5個以下為好。
  • cookie同步session:第一次請求將session存在服務器,並且存入cookie,再次請求,如果在服務器沒取到session,則從cookie中取。
    •   優點:減輕服務器端的壓力
    •   缺點:受到cookie的大小限制,可能占用一定帶寬,因為每次請求會在頭部附帶一定大小的cookie信息,另外這種方式在用戶禁止使用cookie的情況下無效,並且不安全
  • 數據庫同步session,訪問壓力大
  • redis集中管理session
    •   優點:redis為內存數據庫,讀寫效率高,並可在集群環境下做高可用

spring-session + redis解決session共享問題

  1.maven依賴引入

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-web</artifactId>
</dependency>
<!--spring boot 與redis應用基本環境配置 -->
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
<!--spring session 與redis應用基本環境配置 -->
<dependency>
    <groupId>org.springframework.session</groupId>
    <artifactId>spring-session-data-redis</artifactId>
</dependency>
  1. 創建SessionConfig類
import org.springframework.context.annotation.Configuration;
import org.springframework.session.data.redis.config.annotation.web.http.EnableRedisHttpSession;

@Configuration
//設置session的默認在redis中的存活時間
@EnableRedisHttpSession(maxInactiveIntervalInSeconds = 60 * 60 * 8)
public class SessionConfig {
}
  1. 創建SessionInitializer類,初始化session配置
import org.springframework.session.web.context.AbstractHttpSessionApplicationInitializer;
import com.lb.config.SessionConfig;
//初始化Session配置
public class SessionInitializer extends AbstractHttpSessionApplicationInitializer {
    public SessionInitializer() {
        super(SessionConfig.class);
    }
}
  1. application.yml
server:
  port: 8081
spring:
  redis:
    database: '0'
    host: 127.0.0.1
    password: 123456
    pool:
      max-active: 8
      max-idle: 5
      max-wait: 5000
      min-idle: 1
    port: 6379
    timeout: 0
  session:
    store-type: redis   #設置session保存為默認redis的方式
  1. controller實現
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpSession;

import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

@RestController
@SpringBootApplication
public class SessionController {
    @Value("${server.port}")
    private String port;

    @RequestMapping("/setsession")
    public String setSeesion(HttpServletRequest request, String key, String value) {
        HttpSession session = request.getSession();
        session.setAttribute(key, value);
        return "server port :" + port + "---- value :" + value;
    }

    @RequestMapping("/getsession")
    public String getSeesion(HttpServletRequest request, String key) {
        HttpSession session = request.getSession();
        String value = (String) session.getAttribute(key);
        return "server port :" + port + "---- value :" + value;
    }

    public static void main(String[] args) {
        SpringApplication.run(SessionController.class, args);
    }
}

測試用nginx做分發

    #負載均衡分發
    upstream sessionserver {
        server 127.0.0.1:8080;
        server 127.0.0.1:8081;
    }

    server {
        listen       80;
        server_name  localhost;

        #charset koi8-r;

        #access_log  logs/host.access.log  main;

        location / {
            proxy_pass   http://sessionserver;
            index  index.html index.htm;
        }
    }


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM