联合用户的密钥斗篷管理密码

keycloak managed password with federated users

联合用户是否可以通过keycloak管理密码?我有用户 从外部数据库联合,目前也在从外部数据库检查密码。

在外部数据库中创建用户并联合到 keycloak 之后,是否可以在 keycloak 中为该用户注册密码?

我的动机是使用 keycloak 的内置密码重置功能,而不是为联合用户构建额外的 SPI 代码。

Is there a possibility to register a passward in keycloak for the user just after the user is created in external database and then federated to keycloak?

来自 Keycloak Documentation 本身:

By default, Keycloak will import users from LDAP into the local Keycloak user database. This copy of the user is either synchronized on demand, or through a periodic background task. The single exception to this is the synchronization of passwords. Passwords are never imported. Their validation is always delegated to the LDAP server. The benefits of this approach is that all Keycloak features will work as any extra per-user data that is needed can be stored locally. The downside of this approach is that each time that a specific user is queried for the first time, a corresponding Keycloak database insert is performed.

从你的问题中并不清楚,但由于你已经从外部数据库联合用户,我假设你已经实现了你的自定义 UserStorageProvider。您还针对外部数据库验证密码。因此,我假设您还实现了 CredentialInputValidator 接口。如果您尚未实施 CredentialInputUpdater,我认为您要实现的目标应该开箱即用。

如果您已实施 CredentialInputUpdater,您可以尝试执行以下操作: 在 CredentialInputValidator.isvalid 的实现中,首先检查用户是否配置了本地密码,例如像这样

keycloakSession.userCredentialManager().isConfiguredLocally(realm, user, credentialInput.getType())
  • 如果是这种情况(returns true),只需isValid return false。在这种情况下,Keycloak 应该使用其他 CredentialInputValidators 并检查本地配置的密码。
  • 如果不是这种情况 (returns false),请对您的外部数据库进行密码检查。如果密码有效,则静默将密码迁移到 Keycloak 的本地凭证存储。这看起来可能与此类似:
CredentialProvider passwordProvider = keycloakSession.getProvider(CredentialProvider.class, PasswordCredentialProviderFactory.PROVIDER_ID);
if (passwordProvider instanceof CredentialInputUpdater) {
    ((CredentialInputUpdater) passwordProvider).updateCredential(realm, user, credentialInput);
}

CredentialInputUpdater.updateCredential 内确保更新本地存储以及数据库中的密码。

现在您的用户密码将存储在 Keycloak 的本地数据库/凭据存储中,并且内置的密码重置功能应该会按预期工作。