keycloak~關于社區認證的深度總結
keycloak關于社區認證它有統一的設計,社區認證包括了github,microsoft,wechat,qq,dingtalk等等,當然你還可以擴展很多實現了oauth2協議的第三方社區,將它們對接到keycloak上面來,這變得十分容易;社區認證一般由3個provider(SPI)組成,如下所示:
- 社區服務提供者(Identity Provider),繼承了AbstractOAuth2IdentityProvider抽象類,實現了SocialIdentityProvider接口
- 社區服務第一認證流(First Login Flow),當社區用戶與keycloak用戶沒有建立關聯時,會走這個流程
- 社區服務后置認證流(Post Login Flow),當社區用戶與keycloak建立關系后,在執行完
社區服務提供者回調方法后,會走這個流程,完成社區認證最后的步驟
社區認證流程
- 用戶在keycloak認證平臺,點擊第三方社區登錄鏈接
- 跳轉到第三方之后,用戶在第三方完成登錄
- 第三方讓用戶進行確認,是否公開自己的信息,用戶同意之后,302重定向到keycloak社區接口
- 社區接口中通過第三方傳回的code進行用戶token的獲取
- 根據用戶token,調用第三方用戶接口,獲取第三方用戶公開的信息
- 完成keycloak社區認證
- 填充用戶屬性信息
- 走post login flow流程
- 走token生成流程,根據client scope的mapper進行token字段的構建
- 完成登錄后,302到目標頁,帶上keycloak頒發的授權碼
- 目標網站,根據授權碼,獲取keycloak的token接口獲取token
社區綁定事件FEDERATED_IDENTITY_LINK的擴展
- 具體執行的方法:org.keycloak.services.resources.IdentityBrokerService.afterFirstBrokerLogin方法
- 添加自定義事件元素:event.detail(Details.IDENTITY_PROVIDER_USERNAME, context.getBrokerUserId());

社區認證綁定用戶屬性的方式
當社區用戶綁定keycloak用戶后,社區的信息在登錄后,可以自動將它們寫到用戶屬性表里,我們可以通過以下方式來實現
- AbstractJsonUserAttributeMapper的實現類,并通過META-INF/services/org.keycloak.broker.provider.IdentityProviderMapper 來注入它
- 直接在SocialIdentityProvider具體社區實現類中,重寫
updateBrokeredUser方法,進行兩種用戶模塊的映射
社區認證時的state參數構成
1 社區登錄回調state參數,默認由3個參數的拼接而組成,分別是state隨機數,tableId和clientId,而如果我們希望擴展它,讓它支持4個參數,可以這樣操作:
- org.keycloak.broker.provider.util.IdentityBrokerState類中encoded方法

2 構建社區登錄地址時添加自定義state參數
- AbstractOAuth2IdentityProvider類中createAuthorizationUrl方法,修改state參數的拼接
String state = request.getState().getEncoded();
if (request.getAuthenticationSession().getAuthNote("g") != null &&
request.getAuthenticationSession().getAuthNote("g").trim() != "") {
state = state + "." + request.getAuthenticationSession().getAuthNote("g");
}

3 在認證成功后federatedIdentityContext上下文添加參數
- AbstractOAuth2IdentityProvider類中Endpoint.authResponse方法,再返回之前為federatedIdentity添加groupId參數
// 添加集團代碼
String[] decoded = DOT.split(state, 4);
if (decoded.length == 4) {
federatedIdentity.setUserAttribute("g", decoded[3]);
}

社區認證中用戶同步的模式
-
LEGACY(傳統模式):
- 在傳統模式下,Keycloak 會嘗試從外部身份提供程序導入用戶,但如果在 Keycloak 中找不到匹配的用戶,則會創建新用戶。
- 如果在外部提供程序中刪除了用戶,Keycloak 不會自動刪除相應的用戶帳戶,而是將其標記為禁用狀態。
-
IMPORT(導入模式):
- 在導入模式下,Keycloak 會從外部身份提供程序導入用戶,但不會創建新用戶。它只會更新現有用戶的屬性,確保與外部提供程序同步。
- 如果在外部提供程序中刪除了用戶,Keycloak 不會自動刪除用戶帳戶,而是將其標記為禁用狀態。
-
FORCE(強制模式):
- 在強制模式下,Keycloak 會強制執行與外部身份提供程序的完全同步。這意味著它會創建新用戶,更新現有用戶的屬性,同時還會禁用或刪除在 Keycloak 中找不到的用戶。
- 強制模式確保Keycloak中的用戶與外部提供程序中的用戶保持完全同步。
浙公網安備 33010602011771號