keycloak~登入皮膚動態切換的嘗試

张占岭發表於2024-05-10

keycloak的登入皮膚theme,可以設定領域全域性的,或者每個客戶端進行單獨設定,這種設計是沒有問題的,但有時,一個客戶端可能有多種主題,這時,你只能再加個客戶端,對應新的主題,但這樣不方便日後的統計,因為很多統計維度都是以client為基礎的,所以,我們需要在進入登入頁時,讓開發人員轉具體的皮膚引數,然後動態切換皮膚,這個idea不錯。

域全域性皮膚

客戶端個性皮膚

嘗試~自定義ThemeSelectorProvider失敗

這個應該是keycloak不支援多種皮膚,因為它預設透過default皮膚渲染的,咱們新增的,雖然在spi中註冊成功了,但在實現中,並未應用。

  • https://stackoverflow.com/questions/72994502/keycloak-theme-selector-provider-create-not-called
  • https://github.com/dteleguin/keycloak-dynamic-branding/tree/master/keycloak-freemarker-plus
/**
 * KC目前這個定義是未生效的,目前框架只支援預設的DefaultThemeSelectorProvider
 */
public class MyThemeSelectorProvider implements ThemeSelectorProvider {
  KeycloakSession session;

  public MyThemeSelectorProvider(KeycloakSession session) {
    this.session = session;
  }


  @Override
  public String getThemeName(Theme.Type type) {
    return type.name();
  }

  @Override
  public void close() {
  }
}

public class MyThemeSelectorProviderFactory implements ThemeSelectorProviderFactory {

  @Override
  public ThemeSelectorProvider create(KeycloakSession session) {
    return new MyThemeSelectorProvider(session);
  }

  @Override
  public void init(Config.Scope config) {
  }

  @Override
  public void postInit(KeycloakSessionFactory factory) {
  }

  @Override
  public void close() {
  }

  @Override
  public String getId() {
    return "MyThemeSelectorProvider";
  }
}

  • org.keycloak.theme.ThemeSelectorProviderFactory檔案中註冊MyThemeSelectorProviderFactory

最終~還是修改了keycloak原始碼

  • 修改org.keycloak.theme.DefaultThemeSelectorProvider檔案getThemeName()方法,新增請求引數即可

最終的使用

  • https://{keycloak}/auth/realms/{realm}/protocol/openid-connect/auth?theme=你的皮膚名&client_id=account&redirect_uri=&response_type=code&scope=openid
  • keycloak會根據路徑引數中theme的值,動態渲染登入皮膚

相關文章