有這麼個場景,公司下有多個不同網域名稱的站點,我們期望使用者在任意乙個站點下登入後,在開啟另外幾個站點時,也是已經登入的狀態,這麼一過程就是單點登入。
因為多個站點都是用的同一套使用者體系,所以單點登入可以免去使用者重複登入,讓使用者在站點切換的時候更加流暢,甚至是無感知。
單點登入所要實現的就是,某一站點登入後,將其登入態會同步到其他另外幾個站點。
我們分兩部分,先說單個站點的登入流程,再說同步登入態的流程。
我們先看單個站點的登入流程
使用者首次開啟站點,服務端生成session
物件,此時session
中沒有使用者資訊,同時服務端往瀏覽器寫入cookie
使用者觸發登入操作
服務端校驗引數處理登入邏輯後,生成使用者資訊,將使用者資訊寫入session
物件,更新快取redis
我們來畫個圖,如下
乙個站點完成登入後,接下來就是如何讓其他站點也擁有登入態。既然登入態是由cookie
和session
決定的,而cookie
又是由session
寫入的,那麼也就是說,只要把session
同步到其它站點,其它站點只要獲取到session
後,就可以在該網域名稱建立或更新cookie
,這樣一來,兩個不同網域名稱下的站點就擁有相同的登入資訊了。
因此,同步登入態其實就是,如何同步session
的問題。
而我們的session
是採用redis
作為載體,那麼其他站點只要能獲取到redis
中儲存的使用者資訊,不就可以建立自己的session
物件了麼?
沒錯!如何同步session
的問題,就變成了如何讓其他站點從redis
中獲取使用者資訊,也就是如何讓其他站點知道儲存該使用者資訊的redis key
到了這一步,我們需要解決的問題就很明顯啦:如何在不同站點間傳輸使用者憑證。
為便於描述,我們假設有兩個站點,分別為a站點和b站點。因為a、b站點的網域名稱不同,基於同源策略,cookie
是沒法共享的,所以我們採取主動請求的方式,將使用者唯一憑證通過介面傳過去。大致流程如下
a站點完成登入邏輯後,將使用者憑證返回到瀏覽器,為了安全性,在傳輸憑證前,對憑證進行加密,可採用aes
或者rsa
a站點的客戶端獲取到憑證後,呼叫b站點提供的同步登入態介面,將憑證傳過去
b站點的服務端獲取到憑證,解密,查詢快取中的使用者資訊,建立session
物件,寫入b站點網域名稱下的cookie
資訊
b站點的登入態同步完成。
基於上圖,我們完善同步的時序圖
上面描述的是當使用者首次登入時的同步流程,還需要考慮其他場景,比如,b站點獲得的登入態失效了,這時候訪問b站點頁面,就需要在一次前往a站點同步登入態。
b站點上的頁面分為兩種,一種是需要登入態才可以訪問的,一種是不需要登入態就可以訪問的。
第一種情況下,需要重定向到a站點,可為啥要繞回去a站點呢?因為此時我們也不知道a站點的登入態是否也失效了,所以需要回到a站點判斷a站點當前的登入態,若a站點登入態也失效了,那麼就去登陸頁進行重新登入,若a站點是有登陸態的,那麼只要在做一次同步登入態的操作即可。
第二種情況,雖然b頁面不需要登入態就可以檢視,但是企業**往往會在頁面的head部分標記使用者的登入態,所以為了讓這部分的顯示正常,我們在當前頁面非同步的去更新登入態即可。
我們還是來畫圖,清晰一些,如下
若有其他場景,處理的邏輯與這個類似,本質無非就是在獲取一次憑證,重新更新站點快取。
因為要在a站點請求b網域名稱下的介面,所以會有跨域問題,跨域問題常用的解決方式有如下幾種
jsonp
很常見很通用的一種方式
image
利用image src
可以繞過同源策略,所以通過構建乙個image
傳送給請求也是可行的,同時服務端也不需要做太多修改。
cors
老的瀏覽器就沒法支援,需要在服務端設定access-control-allow-origin
,允許任何域或指定的域發起的請求都可以獲取當前伺服器的資料。
多站點單點登入 SSO 設計
為什麼需要單點登入 產品剛上線時,一般由於使用者量少,所有的功能都放在一起,一般也不需要具體的單點登入。隨著使用者量和業務發展的需要,要求逐步將產品按功能或效能分為相應獨立的站點,並分開部署,這就需要在各個站點之間進行單點登入,以達到使用者一次登入,就可以使用多個站點。單點登入的實現 簡單方法 在同...
單點登入系統的設計與實現方案
目的 對目前已有的 web 應用系統,和將來待開發的 web 應用系統系統進行整合,實現單點登入。要求 1.對已有的 web 應用系統不作大規模改造。2.不限制待開發的 web 應用系統的開發工具。3.不增加待開發系統的開發難度。分析 1.目前,已有的系統都各自維護自己的一套使用者庫,每個系統中的使...
單點登入系統的設計與實現方案
目的 對目前已有的 web 應用系統,和將來待開發的 web 應用系統進行整合,實現單點登入。要求 對已有的 web 應用系統不作大規模改造。不限制待開發的 web 應用系統的開發工具。不增加待開發系統的開發難度。分析 目前,已有的系統都各自維護自己的一套使用者庫,每個系統中的使用者數 使用者名稱 ...