Keycloak 异常 "Cannot access delegate without a transaction"

Keycloak exception "Cannot access delegate without a transaction"

上下文:Keycloak 1.9.1.Final 和更新版本

嗨,

我创建了一个自定义用户联合提供程序,它是 Keycloak 的 classpath 属性 联合提供程序示例的简单变体。我没有读取 属性 文件中的用户名,而是从外部网络服务中获取。

我的问题是,有时我在尝试与测试用户进行身份验证时会遇到以下异常:

Failed authentication: java.lang.IllegalStateException: Cannot access delegate without a transaction
  at org.keycloak.models.cache.infinispan.UserCacheSession.getDelegate(UserCacheSession.java:78)
  at org.keycloak.models.cache.infinispan.UserCacheSession.addUser(UserCacheSession.java:442)
  at com.example.keycloak.MyFederationProvider.getUserModel(MyFederationProvider.java:324)
  at com.example.keycloak.MyFederationProvider.getUserByUsername(MyFederationProvider.java:206)
  at org.keycloak.models.UserFederationManager.getUserByUsername(UserFederationManager.java:237)
  at org.keycloak.models.utils.KeycloakModelUtils.findUserByNameOrEmail(KeycloakModelUtils.java:273)
  at org.keycloak.authentication.authenticators.browser.AbstractUsernameFormAuthenticator.validateUserAndPassword(AbstractUsernameFormAuthenticator.java:127)
  at org.keycloak.authentication.authenticators.browser.UsernamePasswordForm.validateForm(UsernamePasswordForm.java:56)
  at org.keycloak.authentication.authenticators.browser.UsernamePasswordForm.action(UsernamePasswordForm.java:49)
  at org.keycloak.authentication.DefaultAuthenticationFlow.processAction(DefaultAuthenticationFlow.java:84)
  at org.keycloak.authentication.AuthenticationProcessor.authenticationAction(AuthenticationProcessor.java:759)
  at org.keycloak.services.resources.LoginActionsService.processFlow(LoginActionsService.java:359)
  at org.keycloak.services.resources.LoginActionsService.processAuthentication(LoginActionsService.java:341)
  at org.keycloak.services.resources.LoginActionsService.authenticateForm(LoginActionsService.java:386)
  ...

我不明白为什么会出现这个异常。我查看了 org.keycloak.models.cache.infinispan.UserCacheSession class 并且我可以看到当 transactionActive 变量为 false 时抛出异常,但我不明白它在什么条件下设置为 false。

我尝试使用 KeycloakModelUtils.runJobInTransaction() 方法或通过在 addUser() 调用周围添加 begin()commit() 来强制进行交易,但它并没有解决问题(我收到一个新错误,通知交易已经激活)。

您是否遇到过这种异常并且知道如何避免它?

非常感谢

我想我可以找到我的错误(或者至少是一个解决方法)。

我的用户联合提供程序的 getInstance() 方法总是返回相同的对象(单例)。我对其进行了更新,以使其在每次调用该方法时都创建一个新的提供程序。

这似乎解决了问题。