首頁  >  文章  >  資料庫  >  redis實作session共享的方法是什麼

redis實作session共享的方法是什麼

PHPz
PHPz轉載
2023-05-30 13:28:062073瀏覽

引言

大廠很多專案都是部署到多台伺服器上,這些伺服器在各個地區都存在,當我們訪問服務時雖然執行的是同一個服務,但是可能是不同伺服器運行的;

在我學習專案時遇到這樣一個登入情景,假設有如下三台伺服器(如圖),就使用session存放使用者的登入信息,透過該資訊可以判斷使用者是否登入:

redis實作session共享的方法是什麼

假設本次登入是透過伺服器01執行的,那麼這次的登入session資訊就存放到了記憶體01中;但是當我再次造訪時卻是伺服器02執行操作,而登入session資訊卻在記憶體01中,伺服器02無法獲取,所以它就會判斷我沒有登錄,回傳錯誤的資訊…

我們想要實現的就是透過一台伺服器登入所產生的session可以和其他伺服器共用,那麼該如何實現?

解決方法 想法就是既然這幾個伺服器自己的記憶體不能共享,那麼只要有一個共享空間供這幾個伺服器共同存取不就可以了(如圖);

redis實作session共享的方法是什麼

首先想到的應該是資料庫,只要這些伺服器叢集共用一個資料庫,並且把產生的session資訊存放到資料庫中不就可以了,這樣大家都可以存取;資料庫有關聯式和非關係型(NoSql):

  • 關係型資料庫:Mysql等

  • 非關係型資料庫:Redis(K /V資料庫)等

這裡其實選擇非關係型資料庫最好,因為Redis基於內存,讀寫效能高,很適合這種使用者資訊頻繁讀取的情況;

還可以透過檔案伺服器實現,這裡就不介紹了;

還有一種方法,可以透過nginx的iphash實現,非常簡單,但是思路和上面兩種不同,原理就是同一個ip的所有請求都會被nginx進行iphash進行計算,將結果綁定到指定伺服器,之後這個請求都會被存取到該伺服器。
但是這樣就有一些問題,首先就算負載平衡就沒有太大意義了,如果綁定的伺服器掛了,那麼iphash也就失效了;又或者你的請求被其他服務分發而未走nginx服務,那麼iphash同樣不生效;所以謹慎使用;

下面我就簡單透過程式碼模擬一下如何透過redis配置輕鬆實現session共享

案例介紹

這裡有一個使用者管理項目,登入邏輯代碼會記錄下來登入使用者的session資訊:

redis實作session共享的方法是什麼

然後同時開啟了該項目的兩個服務:localhost:8080和localhost :8082(可以當作兩台不同伺服器上執行的專案)

redis實作session共享的方法是什麼

#開啟服務後可以存取對應的介面文件:

redis實作session共享的方法是什麼

#-------------------------------------------------分割線-------- -----------------------------------

redis實作session共享的方法是什麼

該服務都有以下兩個介面:(以下測試是在同一個服務中測試的)

登入介面:記錄登入使用者session資訊

redis實作session共享的方法是什麼

登入測試:

redis實作session共享的方法是什麼

取得目前使用者資訊介面:透過登入session取得目前使用者資訊

redis實作session共享的方法是什麼

取得目前登入用戶資訊測試:

redis實作session共享的方法是什麼

因為現在這是兩個服務,所以肯定實作不了共享session的,就算在8080埠的服務登入了,也無法在8082埠的服務取得到目前使用者資訊;(再次強調:上面測試可以取得到目前使用者資訊是因為在同一個服務中測試的,同一個服務session存放到他自己的記憶體當然可以自己存取了)

具體操作

下面就透過redis配置實現共享session:

首先要下載redis,下載網路上找教學;這裡我直接用的在伺服器上透過docker建立的redis容器(簡單好用,強烈建議):

redis實作session共享的方法是什麼

透過視覺化工具可以連接一下:

redis實作session共享的方法是什麼

這樣redis就配置好了,下面在專案程式碼中配置redis:

在專案中引入redis依賴和spring-session設定依賴(自動將session 儲存到redis 中):

<!-- https://mvnrepository.com/artifact/org.springframework.boot/spring-boot-starter-data-redis -->
<dependency>
	<groupId>org.springframework.boot</groupId>
	<artifactId>spring-boot-starter-data-redis</artifactId>
	<version>2.6.4</version>
</dependency>
<!-- https://mvnrepository.com/artifact/org.springframework.session/spring-session-data-redis -->
<dependency>
	<groupId>org.springframework.session</groupId>
	<artifactId>spring-session-data-redis</artifactId>
	<version>2.6.3</version>
</dependency>

在application.yml檔案中設定連接redis和session相關設定:

spring:
  # session配置
  session:
    timeout: 86400 # 设置session失效时间
    store-type: redis # 修改spring-session存储配置,默认存储到服务器内存中,现在设置存到redis中(关键)
  # redis配置
  redis:
    port: 8081 # redis的端口号(这里是我的redis容器在docker中对应的端口号)
    host: xx.xxx.xxx.xxx # 我的云服务器ip
    database: 0 # 设置存入redis的哪一个库(默认是0)

其實關鍵設定就一個: store-type: redis,只要配置了這個,那麼程式碼中session就會存放到redis中而不是自己的記憶體中;

接下來就可以測試了:

呼叫登入接口,生成用戶session信息,查看redis:

redis實作session共享的方法是什麼

可以看到用戶登錄session已經存放到redis中了,這樣我在8080端口登錄,在8082也可以獲得登入的session資訊:

登入:

redis實作session共享的方法是什麼

取得資訊:

redis實作session共享的方法是什麼

這樣就透過redis實作session共享了;

需要注意:引入redis和spring-redis依賴版本需要接近。

以上是redis實作session共享的方法是什麼的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文轉載於:yisu.com。如有侵權,請聯絡admin@php.cn刪除